--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/phonebookui/Phonebook2/UIControls/src/CPbk2ContactEditorDlgImpl.cpp Tue Feb 02 10:12:17 2010 +0200
@@ -0,0 +1,3287 @@
+/*
+* Copyright (c) 2005-2007 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of "Eclipse Public License v1.0"
+* which accompanies this distribution, and is available
+* at the URL "http://www.eclipse.org/legal/epl-v10.html".
+*
+* Initial Contributors:
+* Nokia Corporation - initial contribution.
+*
+* Contributors:
+*
+* Description: Phonebook 2 contact editor dialog implementation.
+*
+*/
+
+
+// INCLUDE FILES
+#include "CPbk2ContactEditorDlgImpl.h"
+
+// Phonebook 2
+#include "Pbk2UIControls.hrh"
+#include "MPbk2ContactEditorStrategy.h"
+#include "CPbk2ContactEditorFieldArray.h"
+#include "MPbk2ContactEditorField.h"
+#include <MPbk2ContactEditorField2.h>
+#include "CPbk2AddItemManager.h"
+#include "Pbk2TitlePanePictureFactory.h"
+#include "TPbk2DeleteItemManager.h"
+#include <MPbk2StoreObservationRegister.h>
+#include <MPbk2ApplicationServices.h>
+#include <CPbk2PresentationContact.h>
+#include <CPbk2PresentationContactField.h>
+#include <CPbk2PresentationContactFieldCollection.h>
+#include <MPbk2FieldProperty.h>
+#include <MPbk2FieldProperty2.h>
+#include <CPbk2FieldPropertyArray.h>
+#include <Pbk2UIControls.rsg>
+#include <MPbk2ContactNameFormatter.h>
+#include <MPbk2ContactEditorExtension.h>
+#include <CPbk2StoreConfiguration.h>
+#include <CPbk2ContactRelocator.h>
+#include <MPbk2ContactEditorEventObserver.h>
+#include <MPbk2EditedContactObserver.h>
+#include <CPbk2UIExtensionManager.h>
+#include <MPbk2UIExtensionFactory.h>
+#include <MPbk2ContactEditorContactRelocator.h>
+#include <CPbk2AppUiBase.h>
+#include <CPbk2StorePropertyArray.h>
+#include <CPbk2StoreProperty.h>
+#include <MPbk2ExitCallback.h>
+#include <CPbk2IconInfoContainer.h>
+#include <CPbk2IconFactory.h>
+#include "Pbk2RingtoneCommands.h"
+#include "Pbk2ImageCommands.h"
+#include "CPbk2ContactEditorUIAddressField.h"
+#include "MPbk2ContactEditorUIField.h"
+#include "Pbk2ContactEditorFieldFactory.h"
+#include "Pbk2AddressTools.h"
+#include "MPbk2UIField.h"
+#include "CPbk2ContactEditorRingtoneField.h"
+#include "CPbk2ContactEditorImageField.h"
+#include "CPbk2ContactEditorReadonlyField.h"
+#include "Pbk2EditorLineIds.hrh"
+#include <Pbk2Config.hrh>
+#include <Pbk2Commands.hrh>
+#include "Pbk2FieldProperty.hrh"
+#include "Pbk2IconId.hrh"
+#include <Pbk2UID.h>
+#include <pbk2mapcommands.hrh>
+
+// Virtual Phonebook
+#include <CVPbkContactManager.h>
+#include <MVPbkStoreContact.h>
+#include <MVPbkContactStore.h>
+#include <MVPbkContactFieldTextData.h>
+#include <MVPbkContactStoreProperties.h>
+#include <MVPbkContactFieldData.h>
+#include <MVPbkFieldType.h>
+#include <TVPbkFieldVersitProperty.h>
+#include <ccappmycardpluginrsc.rsg>
+
+#include <VPbkEng.rsg>
+#include <VPbkFieldType.hrh>
+#include <VPbkContactStoreUris.h>
+
+// System includes
+#include <akntitle.h>
+#include <aknnavi.h>
+#include <StringLoader.h>
+#include <eikcapc.h>
+#include <barsread.h>
+#include <aknnotewrappers.h>
+#include <hlplch.h>
+#include <aknnavide.h>
+#include <akninputblock.h>
+#include <coemain.h>
+
+_LIT( KCCAppMyCardPluginResFileName, "\\resource\\ccappmycardpluginrsc.rsc");
+
+/// Unnamed namespace for local definitions
+namespace {
+
+const TInt KEditorNameFormatFlags = MPbk2ContactNameFormatter::EUseSeparator;
+
+#ifdef _DEBUG
+enum TPanicCode
+ {
+ EHandleControlStateChangeL_NullField = 1,
+ EPanic_IsControlEmptyL_OOB,
+ EPanic_EditorField_OOB
+ };
+
+void Panic(TInt aReason)
+ {
+ _LIT(KPanicText, "CPbk2ContactEditorDlgImpl");
+ User::Panic(KPanicText, aReason);
+ }
+#endif // _DEBUG
+
+/**
+ * Displays a store not available note.
+ *
+ * @param aName Store name.
+ */
+void ShowStoreNotAvailableNoteL( const TDesC& aName )
+ {
+ if ( aName.Length() > 0 )
+ {
+ HBufC* text = StringLoader::LoadLC( R_QTN_PHOB_STORE_NOT_AVAILABLE,
+ aName );
+ CAknInformationNote* note = new ( ELeave ) CAknInformationNote;
+ note->ExecuteLD( *text );
+ CleanupStack::PopAndDestroy( text );
+ }
+ }
+
+/**
+ * Decides whether to leave or not in case of an error.
+ * Performs some filtering of errors.
+ *
+ * @param aError Error code.
+ */
+void DecideToLeaveL( TInt aError )
+ {
+ if ( aError != KErrInUse && aError != KErrNone )
+ {
+ User::Leave( aError );
+ }
+ }
+
+} /// namespace
+
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::CPbk2ContactEditorDlgImpl
+// --------------------------------------------------------------------------
+//
+CPbk2ContactEditorDlgImpl::CPbk2ContactEditorDlgImpl
+ ( TPbk2ContactEditorParams& aParams,
+ CPbk2PresentationContact& aContact,
+ CPbk2FieldPropertyArray& aFieldProperties,
+ MPbk2EditedContactObserver& aContactObserver,
+ MPbk2ContactEditorStrategy& aEditorStrategy,
+ MPbk2ContactEditorContactRelocator& aRelocator,
+ MPbk2ApplicationServices* aAppServices,
+ HBufC* aTitleText ) :
+ iParams( aParams ),
+ iEditorStrategy( aEditorStrategy ),
+ iFieldProperties( aFieldProperties ),
+ iContact( aContact ),
+ iContactObserver( aContactObserver ),
+ iRelocator( aRelocator ),
+ iEndKeyWasPressed( EFalse ),
+ iAddressViewStandalone( EFalse ),
+ iAppServices( aAppServices ),
+ iTitleText( aTitleText ),
+ iPbk2UiResource( *CCoeEnv::Static() )
+ {
+ // Exit is approved by default
+ iExitRecord.Set( EExitApproved );
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::~CPbk2ContactEditorDlgImpl
+// --------------------------------------------------------------------------
+//
+CPbk2ContactEditorDlgImpl::~CPbk2ContactEditorDlgImpl()
+ {
+ if ( iWaitFinish && iWaitFinish->IsStarted() )
+ {
+ iWaitFinish->AsyncStop();
+ }
+ delete iWaitFinish;
+ delete iInputBlock;
+
+ if ( iSelfPtr )
+ {
+ *iSelfPtr = NULL;
+ }
+
+ if( iAppServices )
+ {
+ iAppServices->StoreObservationRegister().DeregisterStoreEvents( *this );
+ }
+ else
+ {
+ Phonebook2::Pbk2AppUi()->ApplicationServices().
+ StoreObservationRegister().DeregisterStoreEvents( *this );
+ }
+
+ if ( iEikonEnv && iContextMenuBar )
+ {
+ iEikonEnv->EikAppUi()->RemoveFromStack( iContextMenuBar );
+ delete iContextMenuBar;
+ }
+
+ // Restore the titlepane text
+ if (iTitlePane && iStoredTitlePaneText)
+ {
+ // iTitlePane takes ownership of iStoredTitlePaneText
+ iTitlePane->SetText(iStoredTitlePaneText);
+ }
+
+ // Reset title pane picture
+ if( iTitlePane )
+ {
+ iTitlePane->SetSmallPicture( NULL, NULL, EFalse );
+ }
+
+ // Remove empty status pane
+ if (iNaviContainer)
+ {
+ iNaviContainer->Pop();
+ }
+
+ delete iStoreContact;
+ delete iFieldFactory;
+ delete iPbk2BaseCommand;
+ delete iEditorExtension;
+ delete iUiFieldArray;
+ Release(iExtensionManager);
+
+ if( iCommandId == EEikCmdExit || iCommandId == EAknCmdExit )
+ {
+ CAknAppUi* appUi = static_cast<CAknAppUi*>( CCoeEnv::Static()->AppUi() );
+
+ if( appUi )
+ {
+ TFileName file;
+ file.Copy( KCCAppMyCardPluginResFileName );
+ iPbk2UiResource.OpenL( file );
+
+ HBufC* title = StringLoader::LoadLC( R_QTN_MYCARD_EDITOR_TITLE );
+
+ iPbk2UiResource.Close();
+ TBool okToExit = EFalse;
+
+ if( iTitleText && iTitleText->CompareC( title->Des() ) == 0 )
+ {
+ okToExit = ETrue;
+ }
+
+ CleanupStack::PopAndDestroy(); // title
+
+ if ( okToExit )
+ {
+ appUi->ProcessCommandL( EAknCmdExit );
+ }
+ }
+ }
+
+ delete iTitleText;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::NewL
+// --------------------------------------------------------------------------
+//
+CPbk2ContactEditorDlgImpl* CPbk2ContactEditorDlgImpl::NewL(
+ TPbk2ContactEditorParams& aParams,
+ CPbk2PresentationContact& aContact,
+ CPbk2FieldPropertyArray& aFieldProperties,
+ MPbk2EditedContactObserver& aContactObserver,
+ MPbk2ContactEditorStrategy& aEditorStrategy,
+ MPbk2ContactEditorContactRelocator& aRelocator)
+ {
+ CPbk2ContactEditorDlgImpl* self =
+ new ( ELeave ) CPbk2ContactEditorDlgImpl(aParams, aContact,
+ aFieldProperties, aContactObserver,
+ aEditorStrategy, aRelocator);
+ CleanupStack::PushL(self);
+ self->ConstructL();
+ CleanupStack::Pop(self);
+ return self;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::NewL
+// --------------------------------------------------------------------------
+//
+CPbk2ContactEditorDlgImpl* CPbk2ContactEditorDlgImpl::NewL(
+ TPbk2ContactEditorParams& aParams,
+ CPbk2PresentationContact& aContact,
+ CPbk2FieldPropertyArray& aFieldProperties,
+ MPbk2EditedContactObserver& aContactObserver,
+ MPbk2ContactEditorStrategy& aEditorStrategy,
+ MPbk2ContactEditorContactRelocator& aRelocator,
+ MPbk2ApplicationServices* aAppServices,
+ HBufC* aTitleText )
+ {
+ CPbk2ContactEditorDlgImpl* self =
+ new ( ELeave ) CPbk2ContactEditorDlgImpl(aParams, aContact,
+ aFieldProperties, aContactObserver,
+ aEditorStrategy, aRelocator, aAppServices, aTitleText );
+ CleanupStack::PushL(self);
+ self->ConstructL();
+ CleanupStack::Pop(self);
+ return self;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ConstructL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::ConstructL()
+ {
+ CAknDialog::ConstructL(R_PBK2_CONTACTEDITOR_MENUBAR);
+
+ if(iParams.iActiveView != TPbk2ContactEditorParams::EEditorView)
+ {
+ iParams.iFocusedContactField = NULL;
+ }
+ if(iParams.iFocusedContactField)
+ {
+ const MVPbkFieldType* type = iParams.iFocusedContactField->BestMatchingFieldType();
+ const TArray<TVPbkFieldVersitProperty> propArr = type->VersitProperties();
+ if(propArr.Count())
+ {
+ const TVPbkFieldVersitProperty prop = propArr[0];
+ if(prop.Name() == EVPbkVersitNameADR)
+ {
+ if(prop.Parameters().Contains(EVPbkVersitParamHOME))
+ {
+ iParams.iActiveView = TPbk2ContactEditorParams::EEditorAddressHomeView;
+ }
+ else if(prop.Parameters().Contains(EVPbkVersitParamWORK))
+ {
+ iParams.iActiveView = TPbk2ContactEditorParams::EEditorAddressOfficeView;
+ }
+ else
+ {
+ iParams.iActiveView = TPbk2ContactEditorParams::EEditorAddressView;
+ }
+ iAddressViewStandalone = ETrue;
+ iParams.iFocusedContactField = NULL;
+ }
+ }
+ }
+
+ // Register to listen store events, so that we can close editor if
+ // iContact's store becomes unavailable.
+
+ /*
+ * Use iAppServices if provided. This is to enable editor use outside from pbk2 context
+ */
+ if( iAppServices )
+ {
+ iAppServices->StoreObservationRegister().RegisterStoreEventsL( *this );
+ iNameFormatter = &iAppServices->NameFormatter();
+ }
+ else
+ {
+ Phonebook2::Pbk2AppUi()->ApplicationServices().
+ StoreObservationRegister().RegisterStoreEventsL( *this );
+ iNameFormatter =
+ &Phonebook2::Pbk2AppUi()->ApplicationServices().NameFormatter();
+ }
+
+
+ StoreTitlePaneTextL();
+ ConstructContextMenuL();
+ ConstructNaviPaneL();
+
+ iExtensionManager = CPbk2UIExtensionManager::InstanceL();
+
+ /*
+ * Use iAppServices if provided. This is to enable editor use outside from pbk2 context
+ */
+ CVPbkContactManager* manager = NULL;
+ if( iAppServices )
+ {
+ manager = &iAppServices->ContactManager();
+ }
+ else
+ {
+ manager = &Phonebook2::Pbk2AppUi()->ApplicationServices().ContactManager();
+ }
+
+ iEditorExtension = iExtensionManager->FactoryL()->
+ CreatePbk2ContactEditorExtensionL( *manager, iContact, *this );
+
+ iFieldFactory = CPbk2ContactEditorFieldFactory::NewL(*this, *iEditorExtension);
+ iUiFieldArray = CPbk2ContactEditorFieldArray::NewL(
+ *manager, iContact, *this, *iFieldFactory, iAppServices );
+
+ iUseState = EUseReady;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ExecuteLD
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::ExecuteLD()
+ {
+ CleanupStack::PushL( this );
+
+ // Set status pane layout to the Phonebook 2 one
+ CEikStatusPane* statusPane = iAvkonAppUi->StatusPane();
+ if (statusPane)
+ {
+ statusPane->SwitchLayoutL(R_AVKON_STATUS_PANE_LAYOUT_USUAL);
+ }
+
+ CleanupStack::Pop( this );
+ CAknForm::ExecuteLD(R_PBK2_EDIT_MEMORY_ENTRY_DIALOG);
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::CreateCustomControlL
+// --------------------------------------------------------------------------
+//
+SEikControlInfo CPbk2ContactEditorDlgImpl::CreateCustomControlL(
+ TInt /*aControlType*/ )
+ {
+ iLastCreatedCustomControl = NULL;
+ SEikControlInfo control = {NULL, 0, 0};
+ iLastCreatedCustomControl = new (ELeave) CPbk2ContactEditorReadonlyField();
+ control.iControl = iLastCreatedCustomControl;
+ control.iTrailerTextId = 0;
+ control.iFlags = 0;
+ return control;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ContactEditorUiBuilderExtension
+// --------------------------------------------------------------------------
+//
+TAny* CPbk2ContactEditorDlgImpl::ContactEditorUiBuilderExtension(
+ TUid /*aExtensionUid*/ )
+ {
+ //return extension point of MPbk2ContactEditorUiBuilderExtension
+ return static_cast<MPbk2ContactEditorUiBuilderExtension*>(this);
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::AddCustomFieldToFormL
+// --------------------------------------------------------------------------
+//
+CCoeControl* CPbk2ContactEditorDlgImpl::AddCustomFieldToFormL(
+ TInt aIndex,TInt aResourceId)
+ {
+ InsertLineL(aIndex, aResourceId);
+ // Return value is updated in CreateCustomControlL()
+ return iLastCreatedCustomControl;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::HandleCustomFieldCommandL
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::HandleCustomFieldCommandL(TInt aCommand )
+ {
+ ProcessCommandL( aCommand );
+ return ETrue;
+ }
+
+// -----------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ConvertCustomControlTypeToBaseControlType()
+// Provide correct base type for custom contols
+// -----------------------------------------------------------------------------
+//
+MEikDialogPageObserver::TFormControlTypes CPbk2ContactEditorDlgImpl::
+ ConvertCustomControlTypeToBaseControlType(TInt aControlType) const
+ {
+ MEikDialogPageObserver::TFormControlTypes ret =
+ MEikDialogPageObserver::EUnknownType;
+
+ switch(aControlType)
+ {
+ case EPbk2FieldCtrlTypeImageEditor:
+ case EPbk2FieldCtrlTypeRingtoneEditor:
+ case EPbk2FieldCtrlTypeExtAddressEditor:
+ case EPbk2FieldCtrlTypeExtAddressHomeEditor:
+ case EPbk2FieldCtrlTypeExtAddressOfficeEditor:
+ case EPbk2FieldCtrlTypeExtAssignFromMapsEditor:
+ {
+ ret = MEikDialogPageObserver::EEdwinDerived;
+ }
+ break;
+ default:
+ {
+ ret = MEikDialogPageObserver::EUnknownType;
+ }
+ break;
+ }
+ return ret;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::HandlePointerEventL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::HandlePointerEventL(
+ const TPointerEvent& aPointerEvent )
+ {
+ //Here we can prevent recursive execution of ExecuteBaseCommandL if needed
+ //as touch events are handled in it too. So it may case multiple callbacks to here if
+ //user repeats the same pointer event very quickly using options menu.
+ // if(!iCommandPending) //seems that this check is not needed
+ {
+ CAknForm::HandlePointerEventL( aPointerEvent );
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::HandleResourceChange
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::HandleResourceChange( TInt aType )
+ {
+ // Handle change in layout orientation
+ if ( aType == KEikDynamicLayoutVariantSwitch )
+ {
+ // Set status pane layout to the Phonebook 2 one
+ CEikStatusPane* statusPane = iAvkonAppUi->StatusPane();
+ if ( statusPane )
+ {
+ TRAP_IGNORE(
+ statusPane->SwitchLayoutL(
+ R_AVKON_STATUS_PANE_LAYOUT_USUAL
+ )
+ );
+ }
+ }
+
+ CAknForm::HandleResourceChange( aType );
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::AddItemToContactL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::AddItemToContactL
+ ( TInt aFieldTypeResourceId,
+ const TDesC& aFieldTypeXspName,
+ TBool aSetFocus )
+ {
+ // Store the original parameter value, since it is
+ // changed by AddFieldsL
+ TInt origParam = aFieldTypeResourceId;
+ TPtrC xSpName = aFieldTypeXspName;
+
+ CPbk2AddItemManager* addItemManager = CPbk2AddItemManager::NewL
+ (iContact, *iUiFieldArray, iParams, iAppServices );
+ CleanupStack::PushL(addItemManager);
+ CPbk2AddItemManager::TReturnValue ret = addItemManager->AddFieldsL(
+ aFieldTypeResourceId, xSpName);
+
+ if (ret.iControlId == KErrAlreadyExists)
+ {
+ // cannot add more than one of this field type
+ // find and focus that
+ TInt fieldArrayCount( iUiFieldArray->Count() );
+ for (TInt i(0); i < fieldArrayCount && ret.iControlId
+ == KErrAlreadyExists; ++i)
+ {
+ if (!iUiFieldArray->At(i).ContactEditorField())
+ {
+ continue;
+ }
+ const MVPbkFieldType* fieldType =
+ iUiFieldArray->At(i).ContactEditorField()->ContactField().
+ BestMatchingFieldType();
+ if(fieldType && fieldType->FieldTypeResId() == aFieldTypeResourceId)
+ {
+ ret.iControlId = iUiFieldArray->At(i).ControlId();
+ }
+ }
+ }
+
+ if (ret.iControlId > 0)
+ {
+ if (aSetFocus)
+ {
+ TryChangeFocusL(ret.iControlId);
+ MPbk2ContactEditorField* editorField = iUiFieldArray->Find( ret.iControlId )->ContactEditorField();
+ MVPbkStoreContactField& storeContactField = editorField->ContactField();
+ iParams.iFocusedContactField = &storeContactField;
+ // Call this after adding or deleting lines
+ UpdatePageL( ETrue );
+ // Must be DrawNow and not DrawDeferred otherwise field label
+ // and content of the following field will be incorrect
+ DrawNow();
+ }
+ }
+ else if (ret.iControlId == KErrNotSupported && origParam == KErrNotFound)
+ {
+ iUiFieldArray->SaveFieldsL();
+ iRelocator.RelocateContactL(aFieldTypeResourceId, xSpName,
+ Pbk2ContactRelocator::EPbk2DisplayStoreDoesNotSupportQuery);
+ }
+ else if ( iParams.iActiveView == TPbk2ContactEditorParams::EEditorView )
+ {
+ switch( ret.iGruopId )
+ {
+ case EPbk2FieldGroupIdPostalAddress:
+ if(iUiFieldArray->Count())
+ {
+ iUiFieldArray->AddNewFieldL( ret.iGruopId );
+ ExecuteAddressDlgL( TPbk2ContactEditorParams::EEditorAddressView );
+ }
+ break;
+ case EPbk2FieldGroupIdHomeAddress:
+ iUiFieldArray->AddNewFieldL( ret.iGruopId );
+ ExecuteAddressDlgL( TPbk2ContactEditorParams::EEditorAddressHomeView );
+ break;
+ case EPbk2FieldGroupIdCompanyAddress:
+ iUiFieldArray->AddNewFieldL( ret.iGruopId );
+ ExecuteAddressDlgL( TPbk2ContactEditorParams::EEditorAddressOfficeView );
+ break;
+ }
+ }
+ CleanupStack::PopAndDestroy(addItemManager);
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::CloseWithoutSaving
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::CloseWithoutSaving( TBool aInformObserver )
+ {
+ CloseDialog(
+ MVPbkContactObserver::EContactOperationUnknown,
+ aInformObserver );
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::TryChangeFocusWithTypeIdL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::TryChangeFocusWithTypeIdL
+ ( TInt aFieldTypeResId, const TDesC& aFieldTypeXSpName )
+ {
+ const TInt count( iUiFieldArray->Count() );
+ for ( TInt i = 0; i < count; ++i )
+ {
+ if (!iUiFieldArray->At(i).ContactEditorField())
+ {
+ continue;
+ }
+ MPbk2ContactEditorField& uiEditorField =
+ *(iUiFieldArray->At(i).ContactEditorField());
+ const MVPbkFieldType* fieldType =
+ uiEditorField.ContactField().BestMatchingFieldType();
+ TInt candidate( KErrNotFound );
+ if ( fieldType )
+ {
+ candidate = fieldType->FieldTypeResId();
+ }
+
+ MPbk2FieldProperty2* fieldPropertyExtension =
+ reinterpret_cast<MPbk2FieldProperty2*>(
+ const_cast<MPbk2FieldProperty&>( uiEditorField.FieldProperty() ).
+ FieldPropertyExtension(
+ KMPbk2FieldPropertyExtension2Uid ) );
+
+ if ( fieldPropertyExtension != NULL )
+ {
+ if ( (aFieldTypeResId == candidate ) &&
+ !fieldPropertyExtension->XSpName().CompareF(
+ aFieldTypeXSpName) )
+ {
+ TryChangeFocusL( uiEditorField.ControlId() );
+ MVPbkStoreContactField& storeContactField = uiEditorField.ContactField();
+ iParams.iFocusedContactField = &storeContactField;
+ // Must be DrawNow and not DrawDeferred otherwise field label
+ // and content of the following field will be incorrect
+ DrawNow();
+ break;
+ }
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::OfferKeyEventL
+// --------------------------------------------------------------------------
+//
+TKeyResponse CPbk2ContactEditorDlgImpl::OfferKeyEventL
+ ( const TKeyEvent& aKeyEvent, TEventCode aType )
+ {
+ TKeyResponse ret(EKeyWasNotConsumed);
+
+ if(iAddressView)
+ {
+ return ret;
+ }
+
+ /* Uncomment this code if it is necessary to enable navigation hardware keys
+ * on devices which have these keys (its Map Extension feature)
+ if( aKeyEvent.iScanCode == EStdKeyApplicationD && aType == EEventKeyUp )
+ {
+ HandleCustomFieldCommandL(EPbk2ExtensionAssignFromMap);
+ return EKeyWasConsumed;
+ }
+
+ if( aKeyEvent.iScanCode == EStdKeyApplicationE && aType == EEventKeyUp )
+ {
+ HandleCustomFieldCommandL(EPbk2ExtensionShowOnMap);
+ return EKeyWasConsumed;
+ }*/
+
+ // Display menu bar if the focused control doesnt consume selection keys
+ CPbk2ContactEditorArrayItem* currentField = iUiFieldArray->Find(
+ IdOfFocusControl());
+
+ if (currentField)
+ {
+ if (currentField->ContactEditorField()
+ && currentField->ContactEditorField()->ConsumesKeyEvent(
+ aKeyEvent, aType))
+ {
+ ret = CAknForm::OfferKeyEventL(aKeyEvent, aType);
+ }
+ else if (currentField->ContactEditorUIField()
+ && currentField->ContactEditorUIField()->ConsumesKeyEvent(
+ aKeyEvent, aType))
+ {
+ ret = CAknForm::OfferKeyEventL(aKeyEvent, aType);
+ }
+ }
+
+ if (ret != EKeyWasConsumed && aType == EEventKey && aKeyEvent.iCode
+ == EKeyOK)
+ {
+ iContextMenuBar->TryDisplayMenuBarL();
+ ret = EKeyWasConsumed;
+ }
+
+ if ( ret != EKeyWasConsumed && !iEndKeyWasPressed )
+ {
+ if ( aKeyEvent.iCode == EKeyEscape )
+ {
+ iEditorStrategy.StopQuery();
+ iEndKeyWasPressed = ETrue;
+ }
+ ret = CAknForm::OfferKeyEventL( aKeyEvent, aType );
+ if ( ret == EKeyWasConsumed &&
+ aKeyEvent.iCode != EKeyPhoneEnd && aKeyEvent.iCode != EKeyEscape )
+ {
+ UpdateCbasL();
+ }
+ }
+
+ return ret;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::GetHelpContext
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::GetHelpContext
+ ( TCoeHelpContext& aContext ) const
+ {
+ if (iParams.iHelpContext)
+ {
+ // If external help context has been set, return it..
+ aContext = *iParams.iHelpContext;
+ }
+ else
+ {
+ // ..otherwise go with the default context
+ iEditorStrategy.GetHelpContext(aContext);
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::PreLayoutDynInitL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::PreLayoutDynInitL()
+ {
+ SetEditableL(ETrue);
+
+ if (!ContactHasAddress(EPbk2FieldGroupIdPostalAddress)
+ && !ContactHasAddress(EPbk2FieldGroupIdHomeAddress)
+ && !ContactHasAddress(EPbk2FieldGroupIdCompanyAddress))
+ {
+ AddGroupFieldsL(EPbk2FieldGroupIdPostalAddress);
+ }
+
+ if(iAddressViewStandalone)
+ {
+ AddGroupFieldsL(Pbk2AddressTools::MapViewTypeToAddress(iParams.iActiveView));
+ }
+
+ iUiFieldArray->CreateFieldsFromContactL(iParams);
+ SetAddressValidationIconsL();
+
+ // Offer button group container to extensions.
+ // This is needed here because previous settings might override extension's
+ // buttons.
+ iEditorExtension->ModifyButtonGroupContainerL(ButtonGroupContainer());
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::PostLayoutDynInitL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::PostLayoutDynInitL()
+ {
+ UpdateTitleL();
+ UpdateTitlePictureL();
+ if(iParams.iFocusedContactField)
+ {
+ const TInt count = iUiFieldArray->Count();
+ for (TInt i = 0; i < count; ++i)
+ {
+ if(iUiFieldArray->At(i).ContactEditorField())
+ {
+ MVPbkBaseContactField & field =
+ iUiFieldArray->At(i).ContactEditorField()->ContactField();
+ if (field.IsSame(*iParams.iFocusedContactField))
+ {
+ UpdateCbasL(&(iUiFieldArray->At(i)));
+ break;
+ }
+ }
+ }
+ }
+ else if(iUiFieldArray->Count())
+ {
+ UpdateCbasL(&(iUiFieldArray->At(0)));
+ }
+
+ // Notify relocator, that editor is ready
+ iRelocator.EditorReadyL();
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::SetInitialCurrentLine
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::SetInitialCurrentLine()
+ {
+ TRAPD( err, ActivateFirstPageL() );
+ if(err)
+ {
+ return;
+ }
+
+ TInt focusedIndex = 0;
+ if ( iParams.iFocusedContactField )
+ {
+ const TInt count = iUiFieldArray->Count();
+ for (TInt i = 0; i < count; ++i)
+ {
+ if (iUiFieldArray->At(i).ContactEditorField())
+ {
+ MVPbkBaseContactField & field =
+ iUiFieldArray->At(i).ContactEditorField()->ContactField();
+ if (field.IsSame(*iParams.iFocusedContactField))
+ {
+ focusedIndex = i;
+ break;
+ }
+ }
+ }
+ CAknForm::SetInitialCurrentLine();
+ iUiFieldArray->SetFocus(focusedIndex);
+ }
+ else
+ {
+ CAknForm::SetInitialCurrentLine();
+ iUiFieldArray->SetFocus(focusedIndex);
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ProcessCommandL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::ProcessCommandL(TInt aCommandId)
+ {
+ HideMenu();
+
+ iContextMenuBar->StopDisplayingMenuBar();
+
+ // Extensions get the command first
+ // If decide to exit already, do not handle new commands until this exit cmd clear
+ if (!iEditorExtension->ProcessCommandL(aCommandId) &&
+ !CheckBaseCommandL(aCommandId) &&
+ !CheckFieldSpecificCommandL(aCommandId) &&
+ iExitRecord.IsClear( EExitOrdered ) )
+ {
+ iCommandId = aCommandId;
+
+ switch (aCommandId)
+ {
+ case EPbk2CmdAddItem:
+ {
+ CmdAddItemL();
+ break;
+ }
+
+ case EPbk2CmdDeleteItem:
+ {
+ CmdDeleteItemL();
+ break;
+ }
+
+ case EPbk2CmdEditItemLabel:
+ {
+ CmdEditItemLabelL();
+ break;
+ }
+#ifdef ECE_DISABLE_CONTEXT_MENU
+ case EPbk2CmdEditorContextMenu:
+ {
+ iContextMenuBar->TryDisplayMenuBarL();
+ break;
+ }
+#endif
+ case EEikCmdExit:
+ case EAknCmdExit:
+ {
+ // Exit Phonebook and if existing save
+ // contact (happens later on in OkToExit..)
+
+ // Escape or end key pressed.
+ // We must save changes and exit the application
+
+ if( iParams.iActiveView == TPbk2ContactEditorParams::EEditorView || iAddressViewStandalone )
+ {
+ if (!iExitRecord.IsSet(EOkToExitWithoutHandlingIt))
+ {
+ if( OkToExitApplicationL( EAknCmdExit ) )
+ {
+ iExitRecord.Set(EExitOrdered);
+ // Remove empty status pane
+ if (iNaviContainer)
+ {
+ iNaviContainer->Pop();
+ iNaviContainer = NULL;
+ }
+
+ MPbk2ContactEditorEventObserver::TParams params;
+ params.iFlags = EPbk2EditorCommandId;
+ params.iKeyCode = EKeyEscape;
+ params.iCommandId = EAknCmdExit;
+
+ CmdDoneL(params);
+ if ( iUseState == EUseOperatingContact )
+ {
+ WaitFinishL();
+ }
+ }
+ }
+ break;
+ }
+ else
+ {
+ if (!iExitRecord.IsSet(EOkToExitWithoutHandlingIt))
+ {
+ iExitRecord.Set(EOkToExitWithoutHandlingIt);
+ OkToExitApplicationL(EAknCmdExit);
+ {
+ // Remove empty status pane
+ if (iNaviContainer)
+ {
+ iNaviContainer->Pop();
+ iNaviContainer = NULL;
+ }
+
+ MPbk2ContactEditorEventObserver::TParams params;
+ params.iFlags = EPbk2EditorKeyCode;
+ params.iKeyCode = EKeyEscape;
+ params.iCommandId = EAknCmdExit;
+
+ CmdDoneL(params);
+ if ( iUseState == EUseOperatingContact )
+ {
+ WaitFinishL();
+ }
+ }
+ }
+ }
+
+ break;
+ }
+ case EAknCmdHelp:
+ {
+ HlpLauncher::LaunchHelpApplicationL(
+ CCoeEnv::Static()->WsSession(),
+ iEikonEnv->EikAppUi()->AppHelpContextL());
+ break;
+ }
+ default:
+ {
+ // Command not handled here, forward it to the app ui.
+ iEikonEnv->EikAppUi()->HandleCommandL(aCommandId);
+ break;
+ }
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::CheckBaseCommandL
+// Check whether there is a base command to execute
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::CheckBaseCommandL(TInt aCommandId)
+ {
+ TBool ret(ETrue);
+ if (!iCommandPending)
+ {
+ //Prevent recursive execution of ExecuteBaseCommandL as touch events are
+ //handled in it too. So it causes multiple callback to here if
+ //user repeats the same pointer event very quickly.
+ iCommandPending = ETrue;
+
+ if (iPbk2BaseCommand)
+ {
+ //Cancel and delete previous possible pending command.
+ delete iPbk2BaseCommand;
+ iPbk2BaseCommand = NULL;
+ }
+ TRAPD(err, ret = ExecuteBaseCommandL(aCommandId));
+ iCommandPending = EFalse;
+ User::LeaveIfError(err);
+ }
+
+ return ret;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ExecuteBaseCommandL
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::ExecuteBaseCommandL(TInt aCommandId)
+ {
+ TBool executingCommand(ETrue);
+
+ switch (aCommandId)
+ {
+ case EPbk2CmdEditorChangeRingtone:
+ {
+ iPbk2BaseCommand = Pbk2RingtoneCommands::SetRingtoneL(
+ &iContact.StoreContact());
+ break;
+ }
+
+ case EPbk2CmdEditorRemoveRingtone:
+ {
+ iPbk2BaseCommand = Pbk2RingtoneCommands::RemoveRingtoneL(
+ &iContact.StoreContact());
+ break;
+ }
+
+ case EPbk2CmdEditorSelectAddress:
+ {
+ ExecuteAddressDlgL(TPbk2ContactEditorParams::EEditorAddressView);
+ return executingCommand;
+ }
+
+ case EPbk2CmdEditorSelectAddressHome:
+ {
+ ExecuteAddressDlgL(TPbk2ContactEditorParams::EEditorAddressHomeView);
+ return executingCommand;
+ }
+
+ case EPbk2CmdEditorSelectAddressOffice:
+ {
+ ExecuteAddressDlgL(
+ TPbk2ContactEditorParams::EEditorAddressOfficeView);
+ return executingCommand;
+ }
+
+ case EPbk2CmdEditorOpen:
+ {
+ CPbk2ContactEditorArrayItem* currentField = iUiFieldArray->Find(
+ IdOfFocusControl());
+
+ if (currentField->ContactEditorUIField())
+ {
+ TPbk2ContactEditorParams::TActiveView
+ viewType =
+ Pbk2AddressTools::MapCtrlTypeToViewType(
+ currentField->ContactEditorUIField()->UIField()->CtrlType());
+ if (viewType != TPbk2ContactEditorParams::EEditorUndefinied)
+ {
+ ExecuteAddressDlgL(viewType);
+ return executingCommand;
+ }
+ }
+ break;
+ }
+ case EPbk2CmdEditorSelectAssignFromMaps:
+ {
+ HandleCustomFieldCommandL(EPbk2ExtensionAssignFromMap);
+ break;
+ }
+
+ case EPbk2CmdEditorAddImage:
+ case EPbk2CmdEditorChangeImage:
+ {
+ iPbk2BaseCommand = Pbk2ImageCommands::SetImageL(
+ &iContact,this);
+ break;
+ }
+
+ case EPbk2CmdEditorViewImage:
+ {
+ iPbk2BaseCommand = Pbk2ImageCommands::ViewImageL(
+ &iContact.StoreContact());
+ break;
+ }
+
+ case EPbk2CmdEditorRemoveImage:
+ {
+ iPbk2BaseCommand = Pbk2ImageCommands::RemoveImageL(&iContact);
+ break;
+ }
+
+ default:
+ {
+ executingCommand = EFalse;
+ break;
+ }
+ }
+
+ if (executingCommand)
+ {
+ CPbk2ContactEditorArrayItem* currentField = iUiFieldArray->Find(
+ IdOfFocusControl());
+
+ if (currentField && currentField->ContactEditorField())
+ {
+ TInt id = currentField->ControlId();
+ TAny
+ * ext =
+ currentField->ContactEditorField()->ContactEditorFieldExtension(
+ TUid::Uid(NULL));
+ if (id == EPbk2EditorLineRingtone)
+ {
+ CPbk2ContactEditorRingtoneField* fld =
+ static_cast<CPbk2ContactEditorRingtoneField*> (ext);
+ fld->SetTextL();
+ }
+ else if( id == EPbk2EditorLineImage &&
+ aCommandId == EPbk2CmdEditorRemoveImage)
+ {
+ //If image removed, no callback to ImageLoadingComplete() so do it here
+ DoImageLoadingCompleteL();
+ }
+ }
+ }
+
+ return executingCommand;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::SwitchView
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::ExecuteAddressDlgL(
+ TPbk2ContactEditorParams::TActiveView aActiveView)
+ {
+ if (iParams.iActiveView == TPbk2ContactEditorParams::EEditorView)
+ {
+ AddGroupFieldsL(Pbk2AddressTools::MapViewTypeToAddress(aActiveView));
+ }
+
+ iParams.iActiveView = aActiveView;
+
+ CPbk2ContactEditorDlgImpl* adressDlg = CPbk2ContactEditorDlgImpl::NewL(
+ iParams, iContact, iFieldProperties, iContactObserver,
+ iEditorStrategy, iRelocator, iAppServices );
+
+ iAddressView = adressDlg;
+ adressDlg->ExecuteLD();
+ iAddressView = NULL;
+ iParams.iActiveView = TPbk2ContactEditorParams::EEditorView;
+ UpdateControlsL();
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::AddAddressFields
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::AddGroupFieldsL(TPbk2FieldGroupId aGroupId)
+ {
+ if (aGroupId == EPbk2FieldGroupIdNone)
+ return;
+
+ TInt count = iFieldProperties.Count();
+ for (TInt idx = 0; idx < count; idx++)
+ {
+ const MPbk2FieldProperty& fieldProp = iFieldProperties.At(idx);
+ if (fieldProp.GroupId() == aGroupId)
+ {
+ AddItemToContactL(fieldProp.FieldType().FieldTypeResId(),
+ KNullDesC(), EFalse);
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::AreAllFieldsEmpty
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::AreAllFieldsEmpty()
+ {
+ TBool result(ETrue);
+ TInt countAll = iContact.PresentationFields().FieldCount();
+ for (TInt idx = 0; idx < countAll; idx++)
+ {
+ CPbk2PresentationContactField& field =
+ iContact.PresentationFields().At(idx);
+
+ MVPbkContactFieldData& data = field.FieldData();
+ TInt fld = field.FieldProperty().FieldType().FieldTypeResId();
+ if(fld != R_VPBK_FIELD_TYPE_RINGTONE &&
+ fld != R_VPBK_FIELD_TYPE_THUMBNAILPIC &&
+ fld != R_VPBK_FIELD_TYPE_CALLEROBJIMG &&
+ fld != R_VPBK_FIELD_TYPE_SYNCCLASS &&
+ fld != R_VPBK_FIELD_TYPE_TOPCONTACT)
+ {
+ if(!data.IsEmpty())
+ {
+ if(data.DataType() == EVPbkFieldStorageTypeText)
+ {
+ HBufC* fieldText = MVPbkContactFieldTextData::Cast(data).Text().AllocL();
+ fieldText->Des().TrimAll();
+ if(fieldText->Length() > 0)
+ {
+ result = EFalse;
+ }
+ delete fieldText;
+ }
+ else
+ {
+ result = EFalse;
+ }
+ }
+ }
+ }
+ return result;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ContactHasAddress
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::ContactHasAddress(
+ TPbk2FieldGroupId aAddressGroup)
+ {
+ TInt countAll = iContact.PresentationFields().FieldCount();
+ for (TInt idx = 0; idx < countAll; idx++)
+ {
+ CPbk2PresentationContactField& field =
+ iContact.PresentationFields().At(idx);
+ if (field.FieldProperty().GroupId() == aAddressGroup)
+ {
+ return ETrue;
+ }
+ }
+ return EFalse;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ClearControls
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::ClearControls()
+ {
+ TInt count = iUiFieldArray->Count();
+ for (TInt idx = count - 1; idx >= 0; idx--)
+ {
+ iUiFieldArray->RemoveFieldFromUI(idx);
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ContactEditorControlExtension
+// --------------------------------------------------------------------------
+//
+TAny* CPbk2ContactEditorDlgImpl::ContactEditorControlExtension(TUid /*aExtensionUid*/)
+ {
+ return static_cast<MPbk2ContactEditorControlExtension*> (this);
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::UpdateControlsL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::UpdateControlsL()
+ {
+ iUiFieldArray->UpdateControlsL();
+ SetAddressValidationIconsL();
+ UpdatePageL(ETrue);
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::CheckFieldSpecificCommandL
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::CheckFieldSpecificCommandL(TInt aCommandId)
+ {
+ TBool ret(EFalse);
+ CPbk2ContactEditorArrayItem* currentField = iUiFieldArray->Find(
+ IdOfFocusControl());
+
+ if (currentField)
+ {
+ if (currentField->ContactEditorUIField())
+ {
+ ret = currentField->ContactEditorUIField()->HandleCustomFieldCommandL(
+ aCommandId);
+ }
+ else
+ {
+ MPbk2ContactEditorField2* tempCurrentField =
+ reinterpret_cast<MPbk2ContactEditorField2*>
+ (currentField->ContactEditorField()->ContactEditorFieldExtension(
+ KMPbk2ContactEditorFieldExtension2Uid));
+ if (tempCurrentField)
+ {
+ ret = tempCurrentField->HandleCustomFieldCommandL(aCommandId);
+ }
+ }
+ }
+
+ return ret;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::DynInitMenuPaneL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::DynInitMenuPaneL(TInt aResourceId,
+ CEikMenuPane* aMenuPane)
+ {
+ iEditorExtension->DynInitMenuPaneL(aResourceId, aMenuPane);
+
+ if (aResourceId == R_PBK2_CONTACTEDITOR_MENUPANE ||
+ aResourceId == R_PBK2_CONTACTEDITOR_CONTEXT_MENUPANE)
+ {
+ //Label editing not anymore supported. Remove later all code
+ //related to editing labels
+ DimItem( aMenuPane, EPbk2CmdEditItemLabel);
+ // Filter delete item away from menu for first and last name fields
+ CPbk2ContactEditorArrayItem* current = iUiFieldArray->Find(
+ IdOfFocusControl());
+ MPbk2ContactEditorField* currentField = current->ContactEditorField();
+ if (currentField)
+ {
+ if (currentField->FieldProperty().Flags()
+ & KPbk2FieldFlagCanNotBeRemoved)
+ {
+ DimItem(aMenuPane, EPbk2CmdDeleteItem);
+ }
+ //Label editing not anymore supported. Remove later all code
+ //related to editing labels
+ //MVPbkStoreContactField& field = currentField->ContactField();
+ //if (!field.SupportsLabel())
+ // {
+ // DimItem( aMenuPane, EPbk2CmdEditItemLabel);
+ // }
+ //else
+ // {
+ // TVPbkFieldVersitProperty prop;
+ // prop.SetName(EVPbkVersitNameIMPP);
+ // if (field.BestMatchingFieldType()->Matches(prop, 0))
+ // {
+ // DimItem( aMenuPane, EPbk2CmdEditItemLabel);
+ // }
+ // }
+ DynInitRingtoneL(aResourceId, aMenuPane, *currentField);
+ DynInitImageL(aResourceId, aMenuPane, *currentField);
+ DynInitSyncL(aResourceId, aMenuPane, *currentField);
+ }
+ else
+ {
+ DimItem(aMenuPane, EPbk2CmdDeleteItem);
+ DimItem(aMenuPane, EPbk2CmdEditorChangeRingtone);
+ DimItem(aMenuPane, EPbk2CmdEditorRemoveRingtone);
+ DimItem(aMenuPane, EPbk2CmdEditorAddImage);
+ DimItem(aMenuPane, EPbk2CmdEditorViewImage);
+ DimItem(aMenuPane, EPbk2CmdEditorChangeImage);
+ DimItem(aMenuPane, EPbk2CmdEditorRemoveImage);
+ DimItem(aMenuPane, EPbk2CmdEditorChangeSync);
+ }
+
+ DynInitAddressL(aResourceId, aMenuPane);
+ // If there are no available fields to add, do not show
+ // the add item dialog. If phone memory is in configuration
+ // this check is not needed.
+ if (!iRelocator.IsPhoneMemoryInConfigurationL())
+ {
+ CArrayPtr<const MPbk2FieldProperty>* availableFields =
+ iContact.AvailableFieldsToAddL();
+ if (!availableFields || availableFields->Count() == 0)
+ {
+ DimItem(aMenuPane, EPbk2CmdAddItem);
+ }
+ delete availableFields;
+ }
+
+ if (aResourceId == R_PBK2_CONTACTEDITOR_MENUPANE)
+ {
+ // Hide exit, if wanted. Exit command is available only in
+ // main menu.
+ if (iParams.iFlags & TPbk2ContactEditorParams::EHideExit)
+ {
+ DimItem(aMenuPane, EAknCmdExit);
+ }
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::DynInitRingtoneL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::DynInitRingtoneL(
+ TInt /*aResourceId*/,
+ CEikMenuPane* aMenuPane,
+ MPbk2ContactEditorField& aCurrentField )
+ {
+ TInt id = aCurrentField.FieldProperty().FieldType().FieldTypeResId();
+
+ if(id != R_VPBK_FIELD_TYPE_RINGTONE)
+ {
+ DimItem( aMenuPane, EPbk2CmdEditorChangeRingtone);
+ DimItem( aMenuPane, EPbk2CmdEditorRemoveRingtone);
+ }
+ else
+ {
+ if( aCurrentField.ContactField().FieldData().DataType() !=
+ EVPbkFieldStorageTypeText ||
+ aCurrentField.ContactField().FieldData().IsEmpty() )
+ {
+ DimItem( aMenuPane, EPbk2CmdEditorRemoveRingtone);
+ }
+ //Label editing not anymore supported (is dimmed in DynInitMenuPaneL)
+ //DimItem( aMenuPane, EPbk2CmdEditItemLabel);
+ DimItem( aMenuPane, EPbk2CmdDeleteItem);
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::DynInitImageL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::DynInitImageL(
+ TInt /*aResourceId*/,
+ CEikMenuPane* aMenuPane,
+ MPbk2ContactEditorField& aCurrentField )
+ {
+ TInt id = aCurrentField.FieldProperty().FieldType().FieldTypeResId();
+
+ if( id != R_VPBK_FIELD_TYPE_CALLEROBJIMG )
+ {
+ DimItem( aMenuPane, EPbk2CmdEditorAddImage );
+ DimItem( aMenuPane, EPbk2CmdEditorViewImage);
+ DimItem( aMenuPane, EPbk2CmdEditorChangeImage);
+ DimItem( aMenuPane, EPbk2CmdEditorRemoveImage);
+ }
+ else
+ {
+ if( aCurrentField.ContactField().FieldData().DataType() ==
+ EVPbkFieldStorageTypeText &&
+ !aCurrentField.ContactField().FieldData().IsEmpty() )
+ {
+ //'View' shown even if there would be cold file name, i.e. no file
+ //available the moment (e.g other mem card). Gallery takes care of
+ //error message. So just dim add option.
+ DimItem( aMenuPane, EPbk2CmdEditorAddImage );
+ }
+ else
+ {
+ DimItem( aMenuPane, EPbk2CmdEditorViewImage);
+ DimItem( aMenuPane, EPbk2CmdEditorChangeImage);
+ DimItem( aMenuPane, EPbk2CmdEditorRemoveImage);
+ }
+
+ //Label editing not anymore supported (is dimmed in DynInitMenuPaneL)
+ //DimItem( aMenuPane, EPbk2CmdEditItemLabel);
+ DimItem( aMenuPane, EPbk2CmdDeleteItem);
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::DynInitSyncL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::DynInitSyncL(
+ TInt /*aResourceId*/,
+ CEikMenuPane* aMenuPane,
+ MPbk2ContactEditorField& aCurrentField )
+ {
+ TInt id = aCurrentField.FieldProperty().FieldType().FieldTypeResId();
+
+ if(id != R_VPBK_FIELD_TYPE_SYNCCLASS)
+ {
+ DimItem( aMenuPane, EPbk2CmdEditorChangeSync);
+ }
+ else
+ {
+ //Label editing not anymore supported (is dimmed in DynInitMenuPaneL)
+ //DimItem( aMenuPane, EPbk2CmdEditItemLabel);
+ }
+ }
+// CPbk2ContactEditorDlgImpl::DynInitAddressL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::DynInitAddressL(TInt /*aResourceId*/,
+ CEikMenuPane* aMenuPane)
+ {
+ CPbk2ContactEditorArrayItem* current = iUiFieldArray->Find(
+ IdOfFocusControl());
+ if (iParams.iActiveView == TPbk2ContactEditorParams::EEditorView)
+ {
+ DimItem(aMenuPane, EPbk2ExtensionAssignFromMapSelect);
+ DimItem(aMenuPane, EPbk2ExtensionAssignFromMap);
+ if (current && current->ContactEditorUIField()
+ && Pbk2AddressTools::MapCtrlTypeToAddress(
+ current->ContactEditorUIField()->UIField()->CtrlType())
+ != EPbk2FieldGroupIdNone)
+ {
+ UnDimItem(aMenuPane, EPbk2CmdEditorOpen);
+ UnDimItem(aMenuPane, EPbk2CmdDeleteItem);
+ }
+ else
+ {
+ DimItem(aMenuPane, EPbk2CmdEditorOpen);
+ }
+ }
+ else
+ {
+ if (!current || !current->ContactEditorUIField()
+ || current->ContactEditorUIField()->UIField()->CtrlType()
+ != EPbk2FieldCtrlTypeExtAssignFromMapsEditor)
+ {
+ DimItem(aMenuPane, EPbk2ExtensionAssignFromMapSelect);
+ }
+ DimItem(aMenuPane, EPbk2CmdAddItem);
+ DimItem(aMenuPane, EPbk2CmdEditorOpen);
+ DimItem(aMenuPane, EPbk2CmdDeleteItem);
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::DimItem
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::DimItem(CEikMenuPane* aMenuPane, TInt aCmd)
+ {
+ TInt pos;
+ if (aMenuPane->MenuItemExists(aCmd, pos))
+ {
+ aMenuPane->SetItemDimmed(aCmd, ETrue);
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::UnDimItem
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::UnDimItem(CEikMenuPane* aMenuPane, TInt aCmd)
+ {
+ TInt pos;
+ if (aMenuPane->MenuItemExists(aCmd, pos))
+ {
+ aMenuPane->SetItemDimmed(aCmd, EFalse);
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::OkToExitL
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::OkToExitL(TInt aKeycode)
+ {
+ TBool ret = EFalse;
+ if( iCommandPending )
+ {
+ //When command in process prevent further processing
+ ret = EFalse;
+ }
+ else if ( iExitRecord.IsSet( EOkToExitWithoutHandlingIt ) )
+ {
+ ret = ETrue;
+ }
+ else if ( aKeycode == EAknSoftkeyDone )
+ {
+ // Done key pressed
+ MPbk2ContactEditorEventObserver::TParams params;
+ params.iFlags = EPbk2EditorKeyCode;
+ params.iKeyCode = aKeycode;
+ CmdDoneL( params );
+ }
+ else if (aKeycode == EKeyEscape || aKeycode == EEikBidCancel)
+ {
+ // this happens when service is canceled, so in this case,
+ // do nothing but give ret ETrue, so that this object
+ // is able to be deleted later.
+ if( iServiceCanceled )
+ {
+ ret = ETrue;
+ }
+ // Escape or end key pressed.
+ // We must save changes and exit the applicatio
+ else if( !iExitRecord.IsSet( EExitOrdered ) )
+ {
+ // Remove empty status pane
+ if (iNaviContainer)
+ {
+ iNaviContainer->Pop();
+ iNaviContainer = NULL;
+ }
+ if ( iStoredTitlePaneText )
+ {
+ delete iStoredTitlePaneText;
+ iStoredTitlePaneText = NULL;
+ }
+ MakeVisible( EFalse );
+ MPbk2ContactEditorEventObserver::TParams params;
+ params.iFlags = EPbk2EditorKeyCode;
+ params.iKeyCode = aKeycode;
+
+ // If the application is not allowed to hide itself in the
+ // background, end of the dialog is also end of the
+ // application.
+ if ( !iAvkonAppUi->ExitHidesInBackground() )
+ {
+ iExitRecord.Set( EExitOrdered );
+
+ if( OkToExitApplicationL( EAknCmdExit ) )
+ {
+ params.iCommandId = EAknCmdExit;
+ }
+ }
+
+ CmdDoneL( params );
+ }
+ }
+ else if (aKeycode == EAknSoftkeyContextOptions)
+ {
+ // Launch context menu if the control is not popup control
+ CEikCaptionedControl* line = CurrentLine();
+ TInt type = line->iControlType;
+ TBool isPopUp = ( type == EAknCtPopupFieldText ) ||
+ ( type == EAknCtPopupField );
+ if (isPopUp)
+ {
+ CAknPopupField* ctrl =
+ static_cast<CAknPopupField*>( line->iControl );
+ ctrl->ActivateSelectionListL();
+ }
+ else
+ {
+ CPbk2ContactEditorArrayItem* current = iUiFieldArray->Find(
+ IdOfFocusControl());
+ if (current && current->ContactEditorUIField())
+ {
+ TPbk2ContactEditorParams::TActiveView
+ viewType =
+ Pbk2AddressTools::MapCtrlTypeToViewType(
+ current->ContactEditorUIField()->UIField()->CtrlType());
+ if (viewType != TPbk2ContactEditorParams::EEditorUndefinied)
+ {
+ ExecuteAddressDlgL(viewType);
+ return ret;
+ }
+ else if (current->ContactEditorUIField()->UIField()->CtrlType()
+ == EPbk2FieldCtrlTypeExtAssignFromMapsEditor)
+ {
+ HandleCustomFieldCommandL(EPbk2ExtensionAssignFromMap);
+ return ret;
+ }
+ }
+
+ iContextMenuBar->SetMenuTitleResourceId(
+ R_PBK2_CONTACTEDITOR_CONTEXT_MENUBAR);
+ iContextMenuBar->SetMenuType(CEikMenuBar::EMenuContext);
+ iContextMenuBar->StopDisplayingMenuBar();
+ iContextMenuBar->TryDisplayMenuBarL();
+ iContextMenuBar->SetMenuTitleResourceId
+ ( R_PBK2_CONTACTEDITOR_MENUBAR );
+ iContextMenuBar->SetMenuType( CEikMenuBar::EMenuOptions );
+ }
+ }
+ else if( aKeycode == EAknSoftkeyChange )
+ {
+ //For custom controls (ringtone, image) msk middle key press need to be
+ //caught here
+ CPbk2ContactEditorArrayItem* current = iUiFieldArray->Find(
+ IdOfFocusControl());
+ MPbk2ContactEditorField* currentField = NULL;
+ if (current)
+ {
+ currentField = current->ContactEditorField();
+ }
+
+ if (currentField)
+ {
+ TInt id = currentField->ControlId();
+ if (id == EPbk2EditorLineRingtone || id == EPbk2EditorLineImage)
+ {
+ MPbk2ContactEditorField2
+ * tempCurrentField =
+ reinterpret_cast<MPbk2ContactEditorField2*> (currentField->ContactEditorFieldExtension(
+ KMPbk2ContactEditorFieldExtension2Uid));
+ if (tempCurrentField)
+ {
+ tempCurrentField->HandleCustomFieldCommandL(
+ EPbk2CmdEditorHandleCustomSelect);
+ }
+ }
+ else
+ {
+ //For non-custom fields (sync...) forward to framework
+ ForwardOkToExitL( aKeycode );
+ }
+ }
+ }
+ else
+ {
+ ForwardOkToExitL( aKeycode );
+ }
+
+ // Clear the exit state after usage.
+ iExitRecord.Clear( EOkToExitWithoutHandlingIt );
+ return ret;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ForwardOkToExitL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::ForwardOkToExitL( TInt aKeycode )
+ {
+ //Prevent further execution of menu commands while a command is running.
+ //In touch tapping RSK very quickly for ringtone gets otherwise through
+ //when ringtone fetch command is running.
+ TBool okToSkip = iCommandPending && aKeycode != EAknSoftkeyDone &&
+ aKeycode != EAknCmdExit && aKeycode != EAknCmdExit;
+ if(!okToSkip)
+ {
+ CAknForm::OkToExitL( aKeycode );
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::HandleControlStateChangeL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::HandleControlStateChangeL(TInt aControlId)
+ {
+ CPbk2ContactEditorArrayItem* current = iUiFieldArray->Find(
+ aControlId);
+ MPbk2ContactEditorField* changedField = current->ContactEditorField();
+ __ASSERT_DEBUG(changedField, Panic(EHandleControlStateChangeL_NullField));
+ if (changedField && iNameFormatter->IsTitleField(
+ changedField->ContactField()))
+ {
+ UpdateTitleL();
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::CreateLineL
+// --------------------------------------------------------------------------
+//
+CCoeControl* CPbk2ContactEditorDlgImpl::CreateLineL
+ ( const TDesC& aCaption, TInt aControlId, TInt aControlType )
+ {
+ return CreateLineByTypeL( aCaption, aControlId, aControlType, NULL );
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::LineControl
+// --------------------------------------------------------------------------
+//
+CEikCaptionedControl* CPbk2ContactEditorDlgImpl::LineControl
+ ( TInt aControlId ) const
+ {
+ return Line( aControlId );
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::DeleteControl
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::DeleteControl(TInt aControlId)
+ {
+ DeleteLine( aControlId );
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::TryChangeFocusL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::TryChangeFocusL(TInt aControlId)
+ {
+ //Ensure current line is set before trying to change focus
+ if(!CurrentLine())
+ {
+ SetInitialCurrentLine();
+ }
+
+ //Attempt setting the focus
+ if ( ControlOrNull( aControlId ) )
+ {
+ TryChangeFocusToL( aControlId );
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::SetCurrentLineCaptionL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::SetCurrentLineCaptionL(const TDesC& aText)
+ {
+ SetControlCaptionL(IdOfFocusControl(), aText);
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::Control
+// --------------------------------------------------------------------------
+//
+CCoeControl* CPbk2ContactEditorDlgImpl::Control(TInt aControlId) const
+ {
+ return ControlOrNull(aControlId);
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::SetEditableL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::SetEditableL( TBool aState )
+ {
+ CAknForm::SetEditableL( aState );
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::LoadBitmapToFieldL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::LoadBitmapToFieldL
+ ( const MPbk2FieldProperty& aFieldProperty,
+ const CPbk2IconInfoContainer& aIconInfoContainer,
+ TInt aControlId )
+ {
+ CPbk2IconFactory* factory = CPbk2IconFactory::NewLC( aIconInfoContainer );
+ CEikImage* image = factory->CreateImageLC( aFieldProperty.IconId() );
+
+ if ( image )
+ {
+ image->SetPictureOwnedExternally( EFalse );
+ image->CopyControlContextFrom( LineControl( aControlId ) );
+ image->SetContainerWindowL( *LineControl( aControlId ) );
+ image->SetNonFocusing();
+ image->SetBrushStyle( CGraphicsContext::ENullBrush );
+
+ delete LineControl( aControlId )->iBitmap;
+ LineControl( aControlId )->iBitmap = image;
+ CleanupStack::Pop( image );
+
+ TRect rect = LineControl( aControlId )->Rect();
+ rect.Resize( -1, -1 );
+ LineControl( aControlId )->SetRect( rect );
+ rect.Resize( 1, 1 );
+ LineControl( aControlId )->SetRect( rect );
+ }
+
+ CleanupStack::PopAndDestroy( factory );
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ContactEditorOperationCompleted
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::ContactEditorOperationCompleted
+ ( MVPbkContactObserver::TContactOpResult aResult,
+ MPbk2ContactEditorEventObserver::TParams aParams )
+ {
+ iUseState = EUseFinished;
+
+ // Notify extensions
+ iEditorExtension->ContactEditorOperationCompleted
+ ( aResult, aParams );
+
+ switch ( aResult.iOpCode )
+ {
+ case MVPbkContactObserver::EContactOperationUnknown: // FALLTHROUGH
+ {
+ CloseDialog( aResult.iOpCode, ETrue );
+ break;
+ }
+ case MVPbkContactObserver::EContactCommit: // FALLTHROUGH
+ case MVPbkContactObserver::EContactDelete:
+ {
+ if ( aParams.iFlags & EPbk2EditorKeyCode &&
+ aParams.iKeyCode == EAknSoftkeyDone )
+ {
+ CloseDialog( aResult.iOpCode, ETrue );
+ }
+ else if ( ( aParams.iFlags & EPbk2EditorKeyCode &&
+ aParams.iKeyCode == EEikBidCancel ) ||
+ ( aParams.iFlags & EPbk2EditorCommandId &&
+ aParams.iCommandId == EEikBidCancel ) )
+ {
+ if( iExitRecord.IsSet( EExitOrdered ) )
+ {
+ ExitApplication( aResult.iOpCode, EAknCmdExit );
+ }
+ else
+ {
+ CloseDialog( aResult.iOpCode, ETrue );
+ }
+ }
+ else if ( ( aParams.iFlags & EPbk2EditorCommandId ) &&
+ ( ( aParams.iCommandId == EEikCmdExit ) ||
+ ( aParams.iCommandId == EAknCmdExit ) ) )
+ {
+ ExitApplication( aResult.iOpCode, aParams.iCommandId );
+ }
+ break;
+ }
+ default:
+ {
+ // Do nothing
+ break;
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::CloseDialog
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::CloseDialog()
+ {
+ // Ignor error and close editor without further user interaction
+ MVPbkContactObserver::TContactOpResult exitResult;
+ exitResult.iExtension = NULL;
+ exitResult.iStoreContact = NULL;
+ exitResult.iOpCode = MVPbkContactObserver::EContactDelete;
+ MPbk2ContactEditorEventObserver::TParams exitParams;
+ if ( iAvkonAppUi->ExitHidesInBackground() )
+ {
+ exitParams.iCommandId = 0;
+ exitParams.iFlags = EPbk2EditorKeyCode;
+ exitParams.iKeyCode = EAknSoftkeyDone;
+ }
+ else
+ {
+ exitParams.iCommandId = EAknCmdExit;
+ exitParams.iFlags = EPbk2EditorCommandId;
+ exitParams.iKeyCode = 0;
+
+ iExitRecord.Set( EExitApproved );
+ iExitRecord.Set( EExitOrdered );
+ }
+
+ ContactEditorOperationCompleted(exitResult, exitParams);
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ContactEditorOperationFailed
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::ContactEditorOperationFailed
+ ( MVPbkContactObserver::TContactOp aOpCode,
+ TInt aErrorCode, MPbk2ContactEditorEventObserver::TParams aParams,
+ MPbk2ContactEditorEventObserver::TFailParams& aFailParams )
+ {
+ iUseState = EUseReady;
+
+ if( iEndKeyWasPressed )
+ {
+ CloseDialog();
+ }
+ else
+ {
+ // Offer the failure to the extensions first
+ iEditorExtension->ContactEditorOperationFailed(aOpCode,
+ aErrorCode, aParams, aFailParams );
+
+ // If extensions did not handle the error, handle it here
+ if ( !aFailParams.iErrorNotified )
+ {
+ CCoeEnv::Static()->HandleError( aErrorCode );
+ }
+
+ if ( aFailParams.iErrorCode != KErrNone )
+ {
+ TPbk2RelocationQyeryPolicy policy(
+ Pbk2ContactRelocator::EPbk2DisplayNoQueries );
+
+ if ( aFailParams.iErrorCode == KErrNotSupported )
+ {
+ policy = Pbk2ContactRelocator::EPbk2DisplayStoreDoesNotSupportQuery;
+ }
+ else if ( aFailParams.iErrorCode == KErrGeneral )
+ {
+ policy = Pbk2ContactRelocator::EPbk2DisplayBasicQuery;
+ }
+
+ TBool result( EFalse );
+ TRAPD( err, result = iRelocator.RelocateContactL( policy ) );
+
+ if ( result )
+ {
+ // Do not close editor if contact need to relocate the first.
+ aFailParams.iCloseEditor = EFalse;
+ }
+
+ if ( err != KErrNone )
+ {
+ CCoeEnv::Static()->HandleError( err );
+ }
+ }
+ // Clear EExitOrdered to let next exit cmd available
+ iExitRecord.Clear(EExitOrdered);
+ if ( aFailParams.iCloseEditor )
+ {
+ CloseDialog( MVPbkContactObserver::EContactOperationUnknown, ETrue );
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::RequestExitL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::RequestExitL(TInt aCommandId)
+ {
+ if (iAddressView)
+ {
+ iAddressView->RequestExitL(aCommandId);
+ }
+
+ if ( iUseState == EUseFinished )
+ {
+ ForceExit();
+ }
+ else if ( iUseState == EUseOperatingContact )
+ {
+ iEditorStrategy.StopQuery();
+ iExitRecord.Set( EExitApproved );
+ iExitRecord.Set( EExitOrdered );
+ }
+ else
+ {
+ if ( aCommandId == EKeyEscape )
+ {
+ iEndKeyWasPressed = ETrue;
+ OkToExitL( EAknSoftkeyDone );
+ // If iUseState is set EUseOperatingContact by above function
+ if ( iUseState == EUseOperatingContact )
+ {
+ WaitFinishL();
+ }
+ }
+ else
+ {
+ iExitRecord.Set( EExitApproved );
+ iExitRecord.Set( EExitOrdered );
+ MPbk2ContactEditorEventObserver::TParams params;
+ params.iFlags = EPbk2EditorCommandId;
+ params.iCommandId = aCommandId;
+ CmdDoneL( params );
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ForceExit
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::ForceExit()
+ {
+ iServiceCanceled = ETrue;
+
+ if (iAddressView)
+ {
+ iAddressView->ForceExit();
+ }
+
+ if ( iUseState == EUseOperatingContact )
+ {
+ iEditorStrategy.StopQuery();
+ iExitRecord.Set( EExitApproved );
+ iExitRecord.Set( EExitOrdered );
+ // It is ignored for dlg would exit
+ // Leave is not valuable
+ TRAP_IGNORE( WaitFinishL() );
+ }
+ else
+ {
+ iExitRecord.Set( EOkToExitWithoutHandlingIt );
+
+ TRAPD( err, TryExitL( EAknSoftkeyBack ) );
+ if ( err != KErrNone )
+ {
+ // If not nicely then use the force
+ delete this;
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ResetWhenDestroyed
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::ResetWhenDestroyed
+ ( MPbk2DialogEliminator** aSelfPtr )
+ {
+ iSelfPtr = aSelfPtr;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::SetFocus
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::SetFocus(TInt aIndex)
+ {
+ TBool found = EFalse;
+ TInt count = 0;
+ TInt idx;
+ for (idx = 0; idx < iUiFieldArray->Count(); idx++)
+ {
+ if (iUiFieldArray->At(idx).ContactEditorField())
+ {
+ if (count == aIndex)
+ {
+ found = ETrue;
+ break;
+ }
+ count++;
+ }
+ }
+ if (found)
+ {
+ iUiFieldArray->SetFocus(idx);
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::NumberOfControls
+// --------------------------------------------------------------------------
+//
+TInt CPbk2ContactEditorDlgImpl::NumberOfControls() const
+ {
+ TInt count = 0;
+ for (TInt idx = 0; idx < iUiFieldArray->Count(); idx++)
+ {
+ if (iUiFieldArray->At(idx).ContactEditorField())
+ {
+ count++;
+ }
+ }
+ return count;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::IndexOfCtrlType
+// --------------------------------------------------------------------------
+//
+TInt CPbk2ContactEditorDlgImpl::IndexOfCtrlType(TPbk2FieldCtrlType aType,
+ TInt& aIndex) const
+ {
+ TInt ret = KErrNotFound;
+ const TInt fieldCount = iUiFieldArray->Count();
+ for (TInt i = Max(aIndex, 0); i < fieldCount; ++i)
+ {
+ if (iUiFieldArray->At(i).ContactEditorField())
+ {
+ const MPbk2FieldProperty & property =
+ iUiFieldArray->At(i).ContactEditorField()->FieldProperty();
+ if (property.CtrlType() == aType)
+ {
+ ret = i;
+ break;
+ }
+ }
+ }
+ return ret;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::AreAllControlsEmpty
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::AreAllControlsEmpty() const
+ {
+ return iUiFieldArray->AreAllUiFieldsEmpty();
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::IsControlEmptyL
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::IsControlEmptyL(TInt aIndex) const
+ {
+ __ASSERT_DEBUG( iUiFieldArray->Count()> aIndex,
+ Panic( EPanic_IsControlEmptyL_OOB ) );
+ TBool ret = EFalse;
+
+ // There are two types field controls in the edit dialog, one is the editor
+ // field control and the other is editor ui field control. The editor field
+ // control are concreted field mapping to one field, it also can be divided
+ // into two types, custom control and normal control. The editor ui field
+ // control are more like a container, currently only be used as the address
+ // container which can contain several editor field controls.
+ if ( iUiFieldArray->At(aIndex).ContactEditorField() )
+ {
+ // The custom control are special controls, like image, ring tone or date,
+ // they need use special way to judge if empty.
+ TBool empty = ETrue;
+ if( IsCustomControlEmptyL(aIndex, empty ) )
+ {
+ ret = empty;
+ }
+ // The control is normal editor field control.
+ else
+ {
+ ret = iUiFieldArray->IsEditorFieldControlEmpty( aIndex );
+ }
+ }
+ // If it's not an editor field control, judge if it's an editor ui field control.
+ else
+ {
+ // Check if contact editor ui field like address field is empty.
+ if ( iUiFieldArray->At( aIndex ).ContactEditorUIField() )
+ {
+ ret = iUiFieldArray->IsEditorUiFieldControlEmpty( aIndex );
+ }
+ }
+
+
+ return ret;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::IsCustomControlEmptyL
+//
+// Check emptiness of those fields that technically may contain data although
+// in view of user and ui are considered as empty (e.g. "Add image" text)
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::IsCustomControlEmptyL(TInt aIndex, TBool& aRet) const
+ {
+ __ASSERT_DEBUG( iUiFieldArray->Count()> aIndex,
+ Panic( EPanic_IsControlEmptyL_OOB ) );
+ TBool isCustom(EFalse);
+ if (!iUiFieldArray->At(aIndex).ContactEditorField())
+ {
+ return isCustom;
+ }
+ MPbk2ContactEditorField& currentField =
+ *(iUiFieldArray->At(aIndex).ContactEditorField());
+ TPbk2FieldCtrlType type = currentField.FieldProperty().CtrlType();
+ TAny* ext = currentField.ContactEditorFieldExtension(TUid::Uid(NULL));
+
+ if (type == EPbk2FieldCtrlTypeImageEditor && ext)
+ {
+ CPbk2ContactEditorImageField* fld =
+ static_cast<CPbk2ContactEditorImageField*> (ext);
+ aRet = fld->TextState() == CPbk2ContactEditorImageField::ENoData;
+ isCustom = ETrue;
+ }
+ else if (type == EPbk2FieldCtrlTypeRingtoneEditor && ext)
+ {
+ CPbk2ContactEditorRingtoneField* fld =
+ static_cast<CPbk2ContactEditorRingtoneField*> (ext);
+ aRet = fld->TextState() == CPbk2ContactEditorRingtoneField::ENoData;
+ isCustom = ETrue;
+ }
+ else if (type == EPbk2FieldCtrlTypeDateEditor)
+ {
+ // If contact has a date field, for index counting
+ // date editor field is considered as a custom control
+ // and it is not empty.
+ isCustom = ETrue;
+ aRet = EFalse;
+ }
+
+ return isCustom;
+ }
+// CPbk2ContactEditorDlgImpl::EditorField
+// --------------------------------------------------------------------------
+//
+MPbk2ContactEditorField& CPbk2ContactEditorDlgImpl::EditorField(TInt aIndex) const
+ {
+ __ASSERT_DEBUG( iUiFieldArray->Count()> aIndex,
+ Panic( EPanic_EditorField_OOB ) );
+
+ TBool found = EFalse;
+ TInt count = 0;
+ TInt idx;
+ for (idx = 0; idx < iUiFieldArray->Count(); idx++)
+ {
+ if (iUiFieldArray->At(idx).ContactEditorField())
+ {
+ if (count == aIndex)
+ {
+ found = ETrue;
+ break;
+ }
+ count++;
+ }
+ }
+
+ __ASSERT_DEBUG( found,
+ Panic( EPanic_EditorField_OOB ) );
+ return *(iUiFieldArray->At(idx).ContactEditorField());
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::StoreReady
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::StoreReady(MVPbkContactStore& /*aContactStore*/)
+ {
+ // Do nothing
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::StoreUnavailable
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::StoreUnavailable
+ ( MVPbkContactStore& aContactStore, TInt /*aReason*/ )
+ {
+ if ( &aContactStore == &iContact.ParentStore() )
+ {
+ /*
+ * Use iAppServices if provided. This is to enable editor use outside from pbk2 context
+ */
+ const CPbk2StoreProperty* property = NULL;
+ if( iAppServices )
+ {
+ property =
+ iAppServices->StoreProperties().FindProperty
+ ( aContactStore.StoreProperties().Uri() );
+ }
+ else
+ {
+ property =
+ Phonebook2::Pbk2AppUi()->ApplicationServices().
+ StoreProperties().FindProperty
+ ( aContactStore.StoreProperties().Uri() );
+ }
+
+
+ TPtrC storeName;
+ if ( property )
+ {
+ storeName.Set( property->StoreName() );
+ }
+
+ // If this leaves the note is not shown.
+ // Cannot do anything about that
+ TRAP_IGNORE( ShowStoreNotAvailableNoteL( storeName ) );
+
+ // Close editor if store which came unavailable is iContact's store
+ iContactObserver.ContactEditingAborted();
+ // TryExitL is not called because it would call OkToExitL
+ // which is not wanted
+ delete this;
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::HandleStoreEventL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::HandleStoreEventL(
+ MVPbkContactStore& /*aContactStore*/,
+ TVPbkContactStoreEvent /*aStoreEvent*/ )
+ {
+ // Do nothing
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::LineChangedL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::LineChangedL( TInt /*aControlId*/ )
+ {
+ SetCbaButtonsL();
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::StoreTitlePaneTextL
+// --------------------------------------------------------------------------
+//
+inline void CPbk2ContactEditorDlgImpl::StoreTitlePaneTextL()
+ {
+ CEikStatusPane* statusPane = iEikonEnv->AppUiFactory()->StatusPane();
+ if (statusPane && statusPane->PaneCapabilities(
+ TUid::Uid(EEikStatusPaneUidTitle)).IsPresent())
+ {
+ iTitlePane = static_cast<CAknTitlePane*>
+ (statusPane->ControlL(TUid::Uid(EEikStatusPaneUidTitle)));
+ if (iTitlePane->Text())
+ {
+ iStoredTitlePaneText = iTitlePane->Text()->AllocL();
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::FocusedControlType
+// --------------------------------------------------------------------------
+//
+TInt CPbk2ContactEditorDlgImpl::FocusedControlType()
+ {
+ CPbk2ContactEditorArrayItem* current = iUiFieldArray->Find(
+ IdOfFocusControl());
+ if (current && current->ContactEditorField())
+ {
+ return current->ContactEditorField()->FieldProperty().CtrlType();
+ }
+ else if (current && current->ContactEditorUIField())
+ {
+ return current->ContactEditorUIField()->UIField()->CtrlType();
+ }
+
+ return EPbk2FieldCtrlTypeNone;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ConstructContextMenuL
+// --------------------------------------------------------------------------
+//
+inline void CPbk2ContactEditorDlgImpl::ConstructContextMenuL()
+ {
+ CEikMenuBar* newMenuBar = new ( ELeave ) CEikMenuBar();
+ CleanupStack::PushL( newMenuBar );
+ newMenuBar->ConstructL
+ ( this, NULL, R_PBK2_CONTACTEDITOR_CONTEXT_MENUBAR );
+ iEikonEnv->EikAppUi()->AddToStackL( newMenuBar, ECoeStackPriorityMenu,
+ ECoeStackFlagRefusesFocus );
+ iContextMenuBar = newMenuBar;
+ CleanupStack::Pop( newMenuBar );
+ iContextMenuBar->SetMenuType( CEikMenuBar::EMenuContext );
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ConstructNaviPaneL
+// --------------------------------------------------------------------------
+//
+inline void CPbk2ContactEditorDlgImpl::ConstructNaviPaneL()
+ {
+ CEikStatusPane* statusPane = iEikonEnv->AppUiFactory()->StatusPane();
+ if (statusPane && statusPane->PaneCapabilities(TUid::Uid(
+ EEikStatusPaneUidNavi)).IsPresent())
+ {
+ // Create a default empty status pane, otherwise sync field will show
+ iNaviContainer
+ = static_cast<CAknNavigationControlContainer *> (statusPane->ControlL(
+ TUid::Uid(EEikStatusPaneUidNavi)));
+ iNaviContainer->PushDefaultL(ETrue);
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::UpdateTitleL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::UpdateTitleL()
+ {
+ if (iTitlePane)
+ {
+ HBufC* title = NULL;
+ switch (iParams.iActiveView)
+ {
+ case TPbk2ContactEditorParams::EEditorAddressView:
+ if( !iTitleText )
+ {
+ title = StringLoader::LoadL(R_QTN_PHOB_HEADER_ADDRESS);
+ }
+ break;
+ case TPbk2ContactEditorParams::EEditorAddressHomeView:
+ if( !iTitleText )
+ {
+ title = StringLoader::LoadL(
+ R_QTN_PHOB_HEADER_ADDRESS_HOME);
+ }
+ break;
+ case TPbk2ContactEditorParams::EEditorAddressOfficeView:
+ if( !iTitleText )
+ {
+ title = StringLoader::LoadL(
+ R_QTN_PHOB_HEADER_ADDRESS_WORK);
+ }
+ break;
+ case TPbk2ContactEditorParams::EEditorView:
+ {
+ if ( !iStoreContact )
+ {
+ // Create the contact once
+ iStoreContact = iContact.StoreContact().ParentStore().CreateNewContactLC();
+ CleanupStack::Pop();
+ }
+
+ // Remove all fields before re-add
+ iStoreContact->RemoveAllFields();
+
+ const TInt fieldCount = iUiFieldArray->Count();
+ for (TInt i = 0; i < fieldCount; ++i)
+ {
+ CPbk2ContactEditorArrayItem& item = iUiFieldArray->At(i);
+ MPbk2ContactEditorField* uiField = item.ContactEditorField();
+ if (uiField && iNameFormatter->IsTitleField(uiField->ContactField()))
+ {
+ HBufC* uiData = uiField->ControlTextL();
+ if (uiData)
+ {
+ CleanupStack::PushL(uiData);
+ const MVPbkFieldType& type =
+ uiField->FieldProperty().FieldType();
+ MVPbkStoreContactField* field = iStoreContact->CreateFieldLC(type);
+ MVPbkContactFieldTextData::Cast(
+ field->FieldData()).SetTextL(*uiData);
+ iStoreContact->AddFieldL(field);
+ CleanupStack::Pop(); // field
+ CleanupStack::PopAndDestroy(uiData);
+ }
+ }
+ }
+ if( !iTitleText )
+ {
+ title = iNameFormatter->GetContactTitleOrNullL(iStoreContact->Fields(),
+ KEditorNameFormatFlags);
+ }
+ break;
+ }
+ default:
+ break;
+ }
+
+ // if custom title text is provided
+ if( iTitleText )
+ {
+ iTitlePane->SetTextL( iTitleText->Des() );
+ }
+ else
+ {
+ if (title)
+ {
+ iTitlePane->SetText(title);
+ }
+ else
+ {
+ iTitlePane->SetTextL(iEditorStrategy.DefaultTitle());
+ }
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::UpdateTitlePictureL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::UpdateTitlePictureL()
+ {
+ if (iTitlePane)
+ {
+ // Update picture in title pane
+
+ /*
+ * Use iAppServices if provided. This is to enable editor use outside from pbk2 context
+ */
+ CEikImage* image = NULL;
+ if( iAppServices )
+ {
+ image =
+ Pbk2TitlePanePictureFactory::CreateTitlePanePictureLC
+ ( &iContact.StoreContact(),
+ iAppServices->StoreProperties() );
+ }
+ else
+ {
+ image =
+ Pbk2TitlePanePictureFactory::CreateTitlePanePictureLC
+ ( &iContact.StoreContact(),
+ Phonebook2::Pbk2AppUi()->ApplicationServices().
+ StoreProperties() );
+ }
+
+
+ // ownership of the picture is transfered to title pane
+ image->SetPictureOwnedExternally( ETrue );
+ iTitlePane->SetSmallPicture(
+ image->Bitmap(), image->Mask(), image->Bitmap() != NULL );
+ // bitmap and mask from image were transfered to title pane,
+ // so image can be destroyed now
+ CleanupStack::PopAndDestroy( image );
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::CloseDialog
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::CloseDialog(
+ MVPbkContactObserver::TContactOp aOpCode, TBool aInformObserver)
+ {
+ if (aInformObserver && iParams.iActiveView
+ == TPbk2ContactEditorParams::EEditorView || iAddressViewStandalone)
+ {
+ switch (aOpCode)
+ {
+ case MVPbkContactObserver::EContactOperationUnknown: // FALLTHROUGH
+ case MVPbkContactObserver::EContactCommit:
+ {
+ iContactObserver.ContactEditingComplete(
+ &iContact.StoreContact());
+ break;
+ }
+ case MVPbkContactObserver::EContactDelete:
+ {
+ iContactObserver.ContactEditingDeletedContact(
+ &iContact.StoreContact());
+ break;
+ }
+ default:
+ {
+ // Either end key was pressed or some uncommon scenario took place,
+ // abort
+ iContactObserver.ContactEditingAborted();
+ break;
+ }
+ };
+ }
+
+ // Don't save any contact data (already saved)
+ iExitRecord.Set(EOkToExitWithoutHandlingIt);
+ iExitRecord.Clear(EExitOrdered);
+
+ // Close dialog using TryExitL and returning ETrue from OkToExit
+ TInt err = KErrNone;
+ TRAP( err, TryExitL( EAknSoftkeyBack ) );
+ if (err != KErrNone)
+ {
+ // If not nicely then use the force.
+ delete this;
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ExitApplication
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::ExitApplication(
+ MVPbkContactObserver::TContactOp aOpCode,
+ TInt aCommandId )
+ {
+ if ( iExitRecord.IsSet( EExitOrdered ) &&
+ iExitRecord.IsSet( EExitApproved ) )
+ {
+
+ CloseDialog( aOpCode, ETrue );
+
+ // Dialog is closed so there is nothing to do if
+ // HandleCommandL leaves.
+ TRAP_IGNORE(CEikonEnv::Static()->EikAppUi()->HandleCommandL(aCommandId));
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::CmdAddItemL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::CmdAddItemL()
+ {
+ AddItemToContactL(KErrNotFound, KNullDesC);
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::CmdDeleteItemL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::CmdDeleteItemL()
+ {
+ TPbk2DeleteItemManager deleteItem( iContact, *iUiFieldArray, iAppServices );
+ if (deleteItem.DeleteFieldL(IdOfFocusControl()))
+ {
+ // Redraw using DrawNow, DrawDeferred does not get the job done
+ DrawNow();
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::CmdEditItemLabelL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::CmdEditItemLabelL()
+ {
+ CPbk2ContactEditorArrayItem* current = iUiFieldArray->Find(
+ IdOfFocusControl());
+ MPbk2ContactEditorField* field = current->ContactEditorField();
+ if (field && field->ContactField().SupportsLabel())
+ {
+ // Find out the presentation contact index and then label length
+ TInt fieldIndx = iContact.PresentationFields().FindFieldIndex(
+ field->ContactField() );
+ TInt maxLabelLength = iContact.PresentationFields().
+ FieldAt( fieldIndx ).MaxLabelLength();
+
+ HBufC* textBuf = HBufC::NewLC(maxLabelLength);
+ TPtr text = textBuf->Des();
+ text.Copy(field->FieldLabel().Left(text.MaxLength()));
+ HBufC* prompt = StringLoader::LoadLC(R_QTN_FORM_PRMPT_FIELD_LABEL);
+
+ CAknTextQueryDialog* dlg = CAknTextQueryDialog::NewL(text);
+ dlg->SetMaxLength(maxLabelLength);
+ if (dlg->ExecuteLD(R_PBK2_EDIT_FIELD_LABEL_QUERY, *prompt))
+ {
+ if (text != field->FieldLabel())
+ {
+ field->SetFieldLabelL(text);
+ }
+ }
+ CleanupStack::PopAndDestroy(2); // prompt, textBuf
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::IsUIDataChanged
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::IsUIDataChanged()
+ {
+ TInt count = iUiFieldArray->Count();
+ for(TInt idx1 = 0; idx1 < count; idx1++)
+ {
+ CPbk2ContactEditorArrayItem& item = iUiFieldArray->At(idx1);
+ if(item.ContactEditorField() && item.ContactEditorField()->FieldDataChanged())
+ {
+ return ETrue;
+ }
+ }
+ return EFalse;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::IsAddressValidated
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::IsAddressValidated(TPbk2FieldGroupId aGroupId)
+ {
+ CPbk2PresentationContactFieldCollection& fields = iContact.PresentationFields();
+ for(TInt idx = 0; idx < fields.FieldCount(); idx++)
+ {
+ MVPbkStoreContactField& field = fields.FieldAt(idx);
+ TInt countProps =
+ field.BestMatchingFieldType()->VersitProperties().Count();
+ TArray<TVPbkFieldVersitProperty> props =
+ field.BestMatchingFieldType()->VersitProperties();
+ for ( TInt idx2 = 0; idx2 < countProps; idx2++ )
+ {
+ if ( props[ idx2 ].Name() == EVPbkVersitNameGEO &&
+ ( ( props[ idx2 ].Parameters().Contains( EVPbkVersitParamHOME ) &&
+ aGroupId == EPbk2FieldGroupIdHomeAddress ) ||
+ ( props[ idx2 ].Parameters().Contains( EVPbkVersitParamWORK ) &&
+ aGroupId == EPbk2FieldGroupIdCompanyAddress ) ||
+ ( !props[ idx2 ].Parameters().Contains( EVPbkVersitParamHOME ) &&
+ !props[ idx2 ].Parameters().Contains( EVPbkVersitParamWORK ) &&
+ aGroupId == EPbk2FieldGroupIdPostalAddress ) ) )
+ {
+ return ETrue;
+ }
+ }
+ }
+ return EFalse;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::SetAddressValidationIconsL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::SetAddressValidationIconsL()
+ {
+ TInt count = iUiFieldArray->Count();
+ for(TInt idx = 0; idx < count; idx++)
+ {
+ CPbk2ContactEditorArrayItem& uiItem = iUiFieldArray->At(idx);
+ MPbk2ContactEditorUIField* uiField = uiItem.ContactEditorUIField();
+ if(uiField)
+ {
+ switch(uiField->UIField()->CtrlType())
+ {
+ case EPbk2FieldCtrlTypeExtAddressEditor:
+ case EPbk2FieldCtrlTypeExtAddressHomeEditor:
+ case EPbk2FieldCtrlTypeExtAddressOfficeEditor:
+ if(IsAddressValidated(Pbk2AddressTools::MapCtrlTypeToAddress(
+ uiField->UIField()->CtrlType())))
+ {
+ TPbk2IconId iconID(TUid::Uid(KPbk2UID3), EPbk2qgn_prop_locev_map);
+ uiField->LoadBitmapToFieldL(iconID);
+ }
+ else
+ {
+ TPbk2IconId iconID(TUid::Uid(KPbk2UID3), EPbk2qgn_prop_pb_no_valid_lm);
+ uiField->LoadBitmapToFieldL(iconID);
+ }
+ break;
+ case EPbk2FieldCtrlTypeExtAssignFromMapsEditor:
+ if(IsAddressValidated( Pbk2AddressTools::MapViewTypeToAddress(iParams.iActiveView)))
+ {
+ TPbk2IconId iconID(TUid::Uid(KPbk2UID3), EPbk2qgn_prop_locev_map);
+ uiField->LoadBitmapToFieldL(iconID);
+ }
+ else
+ {
+ TPbk2IconId iconID(TUid::Uid(KPbk2UID3), EPbk2qgn_prop_pb_no_valid_lm);
+ uiField->LoadBitmapToFieldL(iconID);
+ }
+ break;
+ default:
+ return;
+ }
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::DeleteActiveAddressGeoCoords
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::DeleteActiveAddressGeoCoords()
+ {
+ CPbk2PresentationContactFieldCollection& fields = iContact.PresentationFields();
+ for(TInt idx = 0; idx < fields.FieldCount(); idx++)
+ {
+ MVPbkStoreContactField& field = fields.FieldAt(idx);
+ TInt countProps =
+ field.BestMatchingFieldType()->VersitProperties().Count();
+ TArray<TVPbkFieldVersitProperty> props =
+ field.BestMatchingFieldType()->VersitProperties();
+ for ( TInt idx2 = 0; idx2 < countProps; idx2++ )
+ {
+ if ( props[ idx2 ].Name() == EVPbkVersitNameGEO &&
+ ( ( props[ idx2 ].Parameters().Contains( EVPbkVersitParamHOME ) &&
+ iParams.iActiveView ==
+ TPbk2ContactEditorParams::EEditorAddressHomeView ) ||
+ ( props[ idx2 ].Parameters().Contains( EVPbkVersitParamWORK ) &&
+ iParams.iActiveView ==
+ TPbk2ContactEditorParams::EEditorAddressOfficeView ) ||
+ ( !props[ idx2 ].Parameters().Contains( EVPbkVersitParamHOME ) &&
+ !props[ idx2 ].Parameters().Contains( EVPbkVersitParamWORK ) &&
+ iParams.iActiveView ==
+ TPbk2ContactEditorParams::EEditorAddressView ) ) )
+ {
+ iContact.RemoveField(idx);
+ return;
+ }
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::CmdDoneL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::CmdDoneL(
+ MPbk2ContactEditorEventObserver::TParams& aParams)
+ {
+ // The event that "end" key is pressed is informed into
+ // CPsu2ContactEditorExtension to do some process
+ if( iEndKeyWasPressed )
+ {
+ iEditorExtension->ProcessCommandL( EAknCmdHideInBackground );
+ }
+
+ // Saving/deleting is asynchronic so it is never to ok exit rightaway
+ // No need to save fields when all field are empty.
+ // To estimate dialog is a contact editor or a address dialog.
+ // If it is address dialog, then save all field.
+ if (iUseState != EUseOperatingContact)
+ {
+ if ( !iUiFieldArray->AreAllUiFieldsEmpty()
+ || iParams.iActiveView == TPbk2ContactEditorParams::EEditorAddressView
+ || iParams.iActiveView == TPbk2ContactEditorParams::EEditorAddressHomeView
+ || iParams.iActiveView == TPbk2ContactEditorParams::EEditorAddressOfficeView )
+ {
+ iUiFieldArray->SaveFieldsL();
+ }
+
+ if(iParams.iActiveView != TPbk2ContactEditorParams::EEditorView && IsUIDataChanged() &&
+ IsAddressValidated(Pbk2AddressTools::MapViewTypeToAddress(iParams.iActiveView)))
+ {
+ if(iUiFieldArray->AreAllUiFieldsEmpty())
+ {
+ DeleteActiveAddressGeoCoords();
+ }
+ else
+ {
+ HBufC* prompt = StringLoader::LoadLC(R_QTN_PHOB_CONFIRM_KEEP_COORDINATES);
+ CAknQueryDialog* dlg = CAknQueryDialog::NewL();
+ if(!dlg->ExecuteLD(R_PBK2_GENERAL_CONFIRMATION_QUERY, *prompt))
+ {
+ DeleteActiveAddressGeoCoords();
+ }
+ CleanupStack::PopAndDestroy( prompt );
+ }
+ }
+
+ TInt error(KErrNone);
+ if (iParams.iActiveView == TPbk2ContactEditorParams::EEditorView ||
+ iAddressViewStandalone)
+ {
+ // Estimate all field are empty by UI field.
+ if (( AreAllControlsEmpty() && !iAddressViewStandalone )||
+ (iAddressViewStandalone && AreAllFieldsEmpty()))
+ {
+ if (iEditorExtension->OkToDeleteContactL(aParams))
+ {
+ // iUseState must be set before DeleteContactL() because
+ // during deletion ForceExit() might be entered and needs to
+ // check the state to make sure operation finished.
+ iUseState = EUseOperatingContact;
+
+ // If Endkey is pressed, no need of query dialog in DeleteContactL()
+ if ( iEndKeyWasPressed )
+ {
+ aParams.iCommandId = EEikBidCancel;
+ }
+
+ TRAP( error, iEditorStrategy.DeleteContactL( *this, aParams ) );
+
+ DecideToLeaveL( error );
+ }
+ }
+ else
+ {
+ iParams.iFocusedIndex = FocusedFieldIndexL();
+ if (iEditorExtension->OkToSaveContactL(aParams))
+ {
+ iUseState = EUseOperatingContact;
+
+ TRAP( error, iEditorStrategy.SaveContactL( *this, aParams ) );
+
+ // Close the dialog if save contact fail caused by the
+ // memory full
+ if ( error == KErrDiskFull )
+ {
+ CloseDialog( MVPbkContactObserver::EContactCommit, ETrue );
+ }
+
+ DecideToLeaveL(error);
+ }
+ else
+ {
+ if ( iEndKeyWasPressed )
+ {
+ CloseDialog();
+ }
+ }
+ }
+ }
+ else
+ {
+ CloseWithoutSaving(EFalse);
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::FocusedFieldIndexL
+// --------------------------------------------------------------------------
+//
+TInt CPbk2ContactEditorDlgImpl::FocusedFieldIndexL()
+ {
+ if( iAddressViewStandalone )
+ {
+ return KErrNotFound;
+ }
+
+ const TInt idOfFocusedControl(IdOfFocusControl());
+ TInt fieldIndex(0);
+ const TInt count(iUiFieldArray->Count());
+
+ for (TInt i(0); i < count; ++i)
+ {
+ CPbk2ContactEditorArrayItem& uiField = iUiFieldArray->At(i);
+
+ if(uiField.ControlId() == idOfFocusedControl)
+ {
+ if( IsControlEmptyL(i) )
+ {
+ break;
+ }
+ return fieldIndex;
+ }
+ else
+ {
+ if( !IsControlEmptyL(i) )
+ {
+ fieldIndex++;
+ }
+ }
+ }
+ return KErrNotFound;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::SetCbaButtonsL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::SetCbaButtonsL()
+ {
+ if ( AknLayoutUtils::MSKEnabled() )
+ {
+ TBool hideMsk(EFalse);
+
+ if ( !iRelocator.IsPhoneMemoryInConfigurationL() )
+ {
+ if ( EmptyContextMenuL() )
+ {
+ hideMsk = ETrue;
+ }
+ }
+
+ ButtonGroupContainer().DimCommandByPosition(
+ CEikButtonGroupContainer::EMiddleSoftkeyPosition,
+ hideMsk );
+
+ ButtonGroupContainer().MakeCommandVisibleByPosition(
+ CEikButtonGroupContainer::EMiddleSoftkeyPosition,
+ !hideMsk );
+
+ ButtonGroupContainer().DrawDeferred();
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::EmptyContextMenuL
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::EmptyContextMenuL()
+ {
+ TBool empty(EFalse);
+
+ CPbk2ContactEditorArrayItem* current = iUiFieldArray->Find(
+ IdOfFocusControl());
+
+ if( current )
+ {
+ MPbk2ContactEditorField* currentField = current->ContactEditorField();
+
+ CArrayPtr<const MPbk2FieldProperty>* availableFields =
+ iContact.AvailableFieldsToAddL();
+
+ if ( ( !currentField ||
+ ( currentField->FieldProperty().Flags()
+ & KPbk2FieldFlagCanNotBeRemoved ) ) &&
+ ( !currentField ||
+ !currentField->ContactField().SupportsLabel() ) &&
+ ( !availableFields || availableFields->Count() == 0 ) )
+ {
+ empty = ETrue;
+ }
+ delete availableFields;
+ }
+ else
+ {
+ empty = EFalse;
+ }
+
+ return empty;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::OkToExitApplicationL
+// --------------------------------------------------------------------------
+//
+TBool CPbk2ContactEditorDlgImpl::OkToExitApplicationL
+ ( TInt aCommandId )
+ {
+ TBool okToExit = ETrue;
+
+ // If exit callback returned EFalse, the exit is cancelled
+ if ( iParams.iExitCallback &&
+ !iParams.iExitCallback->OkToExitL( aCommandId ) )
+ {
+ okToExit = EFalse;
+ }
+
+ if ( !okToExit )
+ {
+ iExitRecord.Clear( EExitApproved );
+ }
+
+ return okToExit;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::SetCbaCommandSetL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::SetCbaCommandSetL( TInt aResourceId )
+ {
+ CEikButtonGroupContainer& cba = ButtonGroupContainer();
+ cba.SetCommandSetL( aResourceId );
+ iCbaCommandSet = aResourceId;
+ cba.DrawDeferred();
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::UpdateCbasL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::UpdateCbasL(CPbk2ContactEditorArrayItem* aItemToUpdate)
+ {
+ CPbk2ContactEditorArrayItem* current = aItemToUpdate;
+ if(!current)
+ {
+ current = iUiFieldArray->Find(IdOfFocusControl());
+ }
+
+ MPbk2ContactEditorField* currentField = current->ContactEditorField();
+ MPbk2ContactEditorUIField* currentUIField = current->ContactEditorUIField();
+ if ( currentField )
+ {
+ TPbk2FieldCtrlType type =
+ currentField->FieldProperty().CtrlType();
+ if (type == EPbk2FieldCtrlTypeImageEditor )
+ {
+ TInt id = currentField->ControlId();
+ TAny* ext = currentField->ContactEditorFieldExtension(TUid::Uid(NULL));
+ CPbk2ContactEditorImageField* fld =
+ static_cast<CPbk2ContactEditorImageField*>(ext);
+ if(fld->TextState() == CPbk2ContactEditorImageField::ENoData)
+ {
+ if ( iCbaCommandSet != R_PBK2_SOFTKEYS_OPTIONS_DONE_ADD )
+ {
+ SetCbaCommandSetL( R_PBK2_SOFTKEYS_OPTIONS_DONE_ADD );
+ }
+ }
+ else
+ {
+ if ( iCbaCommandSet != R_PBK2_SOFTKEYS_OPTIONS_DONE_CHANGE )
+ {
+ SetCbaCommandSetL( R_PBK2_SOFTKEYS_OPTIONS_DONE_CHANGE );
+ }
+ }
+ }
+ else if ( type == EPbk2FieldCtrlTypeChoiceItems ||
+ type == EPbk2FieldCtrlTypeRingtoneEditor )
+ {
+ if ( iCbaCommandSet != R_PBK2_SOFTKEYS_OPTIONS_DONE_CHANGE )
+ {
+ SetCbaCommandSetL( R_PBK2_SOFTKEYS_OPTIONS_DONE_CHANGE );
+ }
+ }
+ else
+ {
+#ifndef ECE_DISABLE_CONTEXT_MENU
+ if ( iCbaCommandSet != R_PBK2_SOFTKEYS_OPTIONS_DONE_CONTEXT )
+ {
+ SetCbaCommandSetL( R_PBK2_SOFTKEYS_OPTIONS_DONE_CONTEXT );
+ }
+#else
+ if ( iCbaCommandSet != R_PBK2_SOFTKEYS_OPTIONS_DONE_EMPTY )
+ {
+ SetCbaCommandSetL( R_PBK2_SOFTKEYS_OPTIONS_DONE_EMPTY );
+ }
+#endif
+ }
+ }
+
+ if(currentUIField)
+ {
+ TPbk2FieldCtrlTypeExt type =
+ currentUIField->UIField()->CtrlType();
+ switch(type)
+ {
+ case EPbk2FieldCtrlTypeExtAddressEditor:
+ case EPbk2FieldCtrlTypeExtAddressHomeEditor:
+ case EPbk2FieldCtrlTypeExtAddressOfficeEditor:
+ if ( iCbaCommandSet != R_PBK2_SOFTKEYS_OPTIONS_DONE_CHANGE )
+ {
+ SetCbaCommandSetL( R_PBK2_SOFTKEYS_OPTIONS_DONE_CHANGE );
+ }
+ break;
+ case EPbk2FieldCtrlTypeExtAssignFromMapsEditor:
+ if ( iCbaCommandSet != R_PBK2_SOFTKEYS_OPTIONS_DONE_SELECT )
+ {
+ SetCbaCommandSetL( R_PBK2_SOFTKEYS_OPTIONS_DONE_SELECT );
+ }
+ break;
+ }
+ }
+
+ // Offer button group container to extensions.
+ // This is needed here because previous settings might override extension's
+ // buttons.
+ iEditorExtension->ModifyButtonGroupContainerL(ButtonGroupContainer());
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ImageLoadingComplete
+// --------------------------------------------------------------------------
+//
+TInt CPbk2ContactEditorDlgImpl::ImageLoadingComplete()
+ {
+ TRAPD(err,DoImageLoadingCompleteL())
+ return err;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::DoImageLoadingCompleteL
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::DoImageLoadingCompleteL()
+ {
+ CPbk2ContactEditorArrayItem* currentField =
+ iUiFieldArray->Find(IdOfFocusControl());
+ if (currentField && currentField->ContactEditorField())
+ {
+ TInt id = currentField->ContactEditorField()->ControlId();
+ TAny* ext = currentField->ContactEditorField()->ContactEditorFieldExtension(TUid::Uid(NULL));
+ if( id == EPbk2EditorLineImage )
+ {
+ CPbk2ContactEditorImageField* fld =
+ static_cast<CPbk2ContactEditorImageField*>(ext);
+ fld->SetTextL();
+ }
+ }
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ImageLoadingFailed
+// --------------------------------------------------------------------------
+//
+TInt CPbk2ContactEditorDlgImpl::ImageLoadingFailed()
+ {
+ return KErrNone;
+ }
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::ImageLoadingCancelled
+// --------------------------------------------------------------------------
+//
+TInt CPbk2ContactEditorDlgImpl::ImageLoadingCancelled()
+ {
+ return KErrNone;
+ }
+
+// --------------------------------------------------------------------------
+// CPbk2ContactEditorDlgImpl::WaitFinish
+// --------------------------------------------------------------------------
+//
+void CPbk2ContactEditorDlgImpl::WaitFinishL()
+ {
+ if ( !iWaitFinish && *iSelfPtr )
+ {
+ iInputBlock = CAknInputBlock::NewLC();
+ CleanupStack::Pop( iInputBlock );
+
+ iWaitFinish = new (ELeave) CActiveSchedulerWait();
+ iWaitFinish->Start();
+ }
+ }
+
+// End of File