phonebookui/Phonebook2/UIControls/src/CPbk2ContactEditorDlgImpl.cpp
author Dremov Kirill (Nokia-D-MSW/Tampere) <kirill.dremov@nokia.com>
Wed, 15 Sep 2010 11:56:55 +0300
branchRCL_3
changeset 74 6b5524b4f673
parent 68 9da50d567e3c
child 85 38bb213f60ba
permissions -rw-r--r--
Revision: 201035 Kit: 201036

/*
* 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>
#include <MPbk2StartupMonitor.h>
#include <featmgr.h>

// 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 <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 <charconv.h>
#include <aknpriv.hrh>

/// Unnamed namespace for local definitions
namespace {

const TInt KEditorNameFormatFlags = MPbk2ContactNameFormatter::EUseSeparator;
const TInt KTwoBytes = 2;
const TInt KExtraByte = 1;

#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 ),
        iExitApp( EFalse ),
        iIsInputPaneOpen( EFalse )
    {
    // Exit is approved by default
    iExitRecord.Set( EExitApproved );
    }

// --------------------------------------------------------------------------
// CPbk2ContactEditorDlgImpl::~CPbk2ContactEditorDlgImpl
// --------------------------------------------------------------------------
//
CPbk2ContactEditorDlgImpl::~CPbk2ContactEditorDlgImpl()
    {
    iCoeEnv->RemoveForegroundObserver( *this );

    if ( iWaitFinish && iWaitFinish->IsStarted() )
        {
        iWaitFinish->AsyncStop();
        }
    delete iWaitFinish;
    delete iInputBlock;
    
    if ( iSelfPtr )
        {
        *iSelfPtr = NULL;
        }
    // Make the variable in CloseDialog() to ETrue.
    if ( iDestroyedPtrForCloseDlg )
        {
        *iDestroyedPtrForCloseDlg = ETrue;
        }
    
    // Make the variable in AddItemToContactL() to ETrue.
    if ( iDestroyedPtrForAddItem )
        {
        *iDestroyedPtrForAddItem = ETrue;
        }
    
    if( iAppServices )
        {
        iAppServices->StoreObservationRegister().DeregisterStoreEvents( *this );
        }
    else
        {
        Phonebook2::Pbk2AppUi()->ApplicationServices().
                StoreObservationRegister().DeregisterStoreEvents( *this );
        }
              
    if ( iEikonEnv && iContextMenuBar )
        {
        iEikonEnv->EikAppUi()->RemoveFromStack( iContextMenuBar );
        delete iContextMenuBar;
        }
    
    TRAP_IGNORE ( RestoreStatusPaneL() );    

    // Remove empty status pane
    if (iNaviContainer)
        {
        iNaviContainer->Pop();
        TRAP_IGNORE(RestorePrevNaviDecoratorL());
        }

    delete iStoreContact;
    delete iFieldFactory;
    delete iPbk2BaseCommand;
    delete iEditorExtension;
    delete iUiFieldArray;
    Release(iExtensionManager);
    delete iTitleText;    
    iTitleText = NULL;
    delete iStoredTitlePaneText;
    iStoredTitlePaneText = NULL;

    delete iConverter;
    delete iDelayDelete;
    
    // The if-expression is used here to Exit Phonebook2 for the case 
    // that Exit phonebook2 with the EditorDlg opened.
    if ( iExitApp )
        {
        TRAP_IGNORE( ((CAknViewAppUi*)CEikonEnv::Static()->EikAppUi())->ProcessCommandL( EAknCmdExit ) );
        }
    }

// --------------------------------------------------------------------------
// 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);
    iCoeEnv->AddForegroundObserverL( *this );
    
    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();

    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()
    {
    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.
    // This check is needed, otherwise, when touch quickly on Address field and 
    // quickly on Image field in the Editor Dialog, the address editor will be 
    // opened, but touch input can not open in any of its editors.
    if(!iCommandPending) 
        {
        CAknForm::HandlePointerEventL( aPointerEvent );
        }
    }

// --------------------------------------------------------------------------
// CPbk2ContactEditorDlgImpl::HandleResourceChange
// --------------------------------------------------------------------------
//
void CPbk2ContactEditorDlgImpl::HandleResourceChange( TInt aType )
    {
    switch ( aType )
        {
        case KEikDynamicLayoutVariantSwitch: // Handle change in layout orientation
            {
            // Set status pane layout to the Phonebook 2 one
            CEikStatusPane* statusPane = iAvkonAppUi->StatusPane();
            if ( statusPane )
                {
                iCurrentstatuspane = statusPane->CurrentLayoutResId();
                if( iCurrentstatuspane != R_AVKON_STATUS_PANE_LAYOUT_USUAL )
                    {
                    TRAP_IGNORE( 
                        statusPane->SwitchLayoutL(
                            R_AVKON_STATUS_PANE_LAYOUT_USUAL )
                        );
                    }
                }
            }
            break;
        case KAknSplitInputEnabled:     // Handle split input keyboard
            {
            // Sometimes this function will be called continuously
            // with the same parameter.
            // Add a flag iIsInputPaneOpen to ensure the dialog
            // only draw one time.
            if( !iIsInputPaneOpen )
                {
                Layout();
                DrawNow();
                iIsInputPaneOpen = ETrue;
                }
            }
            break;
        case KAknSplitInputDisabled:
            {
            // Sometimes this function will be called continuously
            // with the same parameter.
            // Add a flag iIsInputPaneOpen to ensure the dialog
            // only draw one time.
            if( iIsInputPaneOpen )
                {
                // Set status pane layout to the Phonebook 2 one
                Layout();
                DrawNow();
                CEikStatusPane* statusPane = iAvkonAppUi->StatusPane();
                if ( statusPane )
                    {
                    TRAP_IGNORE(
                            statusPane->SwitchLayoutL(
                                    R_AVKON_STATUS_PANE_LAYOUT_USUAL )
                        );
                    }
                iIsInputPaneOpen = EFalse;
                }
            }
            break;
        default:
            break;
        }
    
    CAknForm::HandleResourceChange( aType );
    }

// --------------------------------------------------------------------------
// CPbk2ContactEditorDlgImpl::AddItemToContactL
// --------------------------------------------------------------------------
//
void CPbk2ContactEditorDlgImpl::AddItemToContactL
      ( TInt aFieldTypeResourceId,
        const TDesC& aFieldTypeXspName, 
        TBool aSetFocus )
    {
    // For knowing whether the destructor has been called
    TBool destroyed = EFalse;
    iDestroyedPtrForAddItem = &destroyed;
    // 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);
    
    // In case that pop list for adding item is closed by FSW, this object 
    // will be destructed by CPbk2ContactEditorOperator::ForceExit().
    // If this object is destructed, don't execute the following anymore.
    if ( !destroyed )
        {
        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;
                }
            }
        iDestroyedPtrForAddItem = NULL;
        }
    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;
         }*/

     // When the end key is pressed and OfferKeyEventL() is called for the first time,
     // set the edit dialog to be not editable to close the partial input
     // screen if it is open.
     if( aKeyEvent.iCode == EKeyEscape && !iEndKeyWasPressed )
         {
         SetEditableL( EFalse );
         }

    // Display menu bar if the focused control doesnt consume selection keys
    CPbk2ContactEditorArrayItem* currentField = iUiFieldArray->Find(
            IdOfFocusControl());

    if (currentField)
        {
        CheckCurrentFieldTextL( currentField, aKeyEvent, aType );
    
        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 )
        {
        // If the iEndKeyWasPressed equels to true, which illustrates
        // the EditorDlgImpl get the Escape key event one more time 
        // for the case that Exit phonebook2 with the EditorDlg opened,
        // sush as save VOIP settings,there will be two event,
        // one is to close dialog and the other is to exit phonebook2. 
        if ( iEndKeyWasPressed )
            {
            if ( aKeyEvent.iCode == EKeyEscape && iAvkonAppUi->IsAppShutterRunning() )
                {
                // Use the iExitApp to record whether the AppShutter is running.
                // According to the value of iExitApp to Exit Phonebook2 app ui 
                // after the EditorDlg close completely. 
                iExitApp = ETrue;
                }
            }
        else
            {
            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());

    ConstructNaviPaneL();
    UpdateTitleL();
    UpdateTitlePictureL();
    }

// --------------------------------------------------------------------------
// CPbk2ContactEditorDlgImpl::PostLayoutDynInitL
// --------------------------------------------------------------------------
//
void CPbk2ContactEditorDlgImpl::PostLayoutDynInitL()
    {
    
    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()
    {
    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 ) )
        {
        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();
                                RestorePrevNaviDecoratorL();
                                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();
                                RestorePrevNaviDecoratorL();
                                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();
    
    // The if-expression refers to the situation that need to
    // delete editor dialog after address dialog exit completely,
    // such as the store-unavailable situation    
    if ( iDelayDelete )
        {
        iDelayDelete->Start( TCallBack( &DelayDlgDeleteCallBack, this ) );
        }
    }

// --------------------------------------------------------------------------
// CPbk2ContactEditorDlgImpl::DelayDlgDeleteCallBack
// --------------------------------------------------------------------------
//
TInt CPbk2ContactEditorDlgImpl::DelayDlgDeleteCallBack( TAny* aCallBack )
    {
    static_cast<CPbk2ContactEditorDlgImpl*>( aCallBack )->DelayDlgDelete();
    return EFalse;    
    }

// --------------------------------------------------------------------------
// CPbk2ContactEditorDlgImpl::DelayDlgDelete
// --------------------------------------------------------------------------
//
void CPbk2ContactEditorDlgImpl::DelayDlgDelete()
    {
    // Need to inform editor-observer that contact editing is
    // aborted, at the same time, exit editor dialog directly 
    // without saving the changes.
    iContactObserver.ContactEditingAborted();
    delete this;
    }

// --------------------------------------------------------------------------
// 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::AreAllFieldsEmptyL()
    {
    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() )
            {
            DimItem( aMenuPane, EPbk2CmdEditorAddImage );
            
            //Dim 'View image' if currently cold file name, e.g mem card not there.
            TBool dimView(ETrue);
            TPbk2FieldCtrlType type = aCurrentField.FieldProperty().CtrlType();
            TAny* ext = aCurrentField.ContactEditorFieldExtension(TUid::Uid(NULL));
            if (type == EPbk2FieldCtrlTypeImageEditor && ext)
                {
                CPbk2ContactEditorImageField* fld =
                        static_cast<CPbk2ContactEditorImageField*> (ext);
                TPtrC dataPtr(MVPbkContactFieldTextData::Cast(  
                        fld->ContactField().FieldData()).Text());
                TEntry entry;
                RFs& fs( iCoeEnv->FsSession() );        
                dimView = fs.Entry( dataPtr, entry ) == 0 ? EFalse : ETrue;
                }        
            if( dimView )
                {
                DimItem( aMenuPane,  EPbk2CmdEditorViewImage);
                }
            }
        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 the selection popup is open, hide menu option "Change" 
    if( id == R_VPBK_FIELD_TYPE_SYNCCLASS ) 
        {
        CEikCaptionedControl* line=CurrentLine();  
        if ( line && (line->iControlType == EAknCtPopupField || line->iControlType == EAknCtPopupFieldText ) )
            {
            CAknPopupField* ctrl = static_cast<CAknPopupField*>( line->iControl );
            if ( ctrl && ctrl->NumLines() > 1 ) 
                {
                DimItem( aMenuPane, EPbk2CmdEditorChangeSync);
                }
            }
        }
    else  // id != R_VPBK_FIELD_TYPE_SYNCCLASS
        { 
        DimItem( aMenuPane,  EPbk2CmdEditorChangeSync);
        }
    
    }
// CPbk2ContactEditorDlgImpl::DynInitAddressL
// --------------------------------------------------------------------------
//
void CPbk2ContactEditorDlgImpl::DynInitAddressL(TInt /*aResourceId*/,
        CEikMenuPane* aMenuPane)
    {
    CPbk2ContactEditorArrayItem* current = iUiFieldArray->Find(
            IdOfFocusControl());
    if (iParams.iActiveView == TPbk2ContactEditorParams::EEditorView)
        {
        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
        {
        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();
                 RestorePrevNaviDecoratorL();
                 iNaviContainer = NULL;
                 }
            
            if ( !iAvkonAppUi->IsAppShutterRunning() )
                {
                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 );
    TRAP_IGNORE( UpdateTitleL() );    
    }

// --------------------------------------------------------------------------
// 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 )
        {
        CEikCaptionedControl* line = LineControl( aControlId );
        if( line )
            {
            line->SetIconL( 
                const_cast<CFbsBitmap*>( image->Bitmap() ), 
                const_cast<CFbsBitmap*>( image->Mask() ) );
            line->iBitmap->SetPictureOwnedExternally( EFalse );
            image->SetPictureOwnedExternally( ETrue );
            line->iBitmap->SetNonFocusing();
            line->iBitmap->SetBrushStyle( CGraphicsContext::ENullBrush );
            line->iBitmap->SetContainerWindowL( *line );
            }

        CleanupStack::PopAndDestroy( image );
        }

    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()
    {
    // Ignore 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 ) );

        // If the address dialog is opened, delete address dialog first,
        // then after address dialog exit completely, delete the editor dialog
        // via DelayDlgDeleteCallBack; if there isn't the address dialog, 
        // delete editor dialog directly.         
        if (iAddressView )
            {
            // Create the CIdle object to delete editor dialog later.
            if ( !iDelayDelete )
                {
                iDelayDelete = CIdle::NewL( CActive::EPriorityStandard );
                }
            delete iAddressView;
            iAddressView = NULL;
            }
       else
            {
            // At the store unavailable situation, informs editor observer 
            // that contact editing is aborted without saving the changes.
            iContactObserver.ContactEditingAborted();
            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)));
        
        iPrevNaviDecorator =  iNaviContainer->Top();        
        
        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());
                }
            }
        }
    CEikStatusPane* statusPane = iAvkonAppUi->StatusPane();
    
    if (statusPane)
        {
        iCurrentstatuspane = statusPane->CurrentLayoutResId();
        if( iCurrentstatuspane != R_AVKON_STATUS_PANE_LAYOUT_USUAL )
            {
            statusPane->SwitchLayoutL(R_AVKON_STATUS_PANE_LAYOUT_USUAL);
            }
        }
        
    }

// --------------------------------------------------------------------------
// 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)
    {
    // For knowing if the destructor has been called
    TBool destroyed = EFalse;
    iDestroyedPtrForCloseDlg = &destroyed;

    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;
                }
            };
        }

    // In VOIP/new contacts/exit case, this object will be destructed by
    // iContactObserver.ContactEditingComplete() above.
    // If this object is destructed, don't excute the following anymore
    if ( !destroyed )
        {
        // 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;
            }
        iDestroyedPtrForCloseDlg = NULL;
        }
    }

// --------------------------------------------------------------------------
// 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:
                    {
                	TInt iconId = 0;
                    // UnSync feature indicator flag and chinese flag
                    TBool supportUnSyncFeature = 
                          FeatureManager::FeatureSupported( 
                          KFeatureIdFfTdUnSyncabPbfieldsInd );
                    TBool supportChinese = 
                        FeatureManager::FeatureSupported( KFeatureIdChinese ); 
                    // Valid address
                    TBool addressValidated = 
                         IsAddressValidated( 
                            Pbk2AddressTools::MapCtrlTypeToAddress(
                            uiField->UIField()->CtrlType()));
                    if(supportChinese && supportUnSyncFeature)
                        {
                        // Unsync icon
                        iconId = EPbk2qgn_prop_phonebook2_unsync;
                        }
                    else
                        {
                        iconId = addressValidated ?
                            EPbk2qgn_prop_locev_map : EPbk2qgn_prop_pb_no_valid_lm;
                        }
                    TPbk2IconId pbkIconId(TUid::Uid(KPbk2UID3),iconId);
                    uiField->LoadBitmapToFieldL(pbkIconId); 
                    }
                    break;
                case EPbk2FieldCtrlTypeExtAssignFromMapsEditor:
                    {
                    // UnSync feature indicator flag and chinese flag
                    TBool supportUnSyncFeature = 
                           FeatureManager::FeatureSupported(
                           KFeatureIdFfTdUnSyncabPbfieldsInd );
                    TBool supportChinese = 
                           FeatureManager::FeatureSupported( KFeatureIdChinese ); 

                    TBool addressValidated = 
                           IsAddressValidated( 
                           Pbk2AddressTools::MapViewTypeToAddress( iParams.iActiveView ));
                    TInt iconId = 0;
                    if( supportChinese && supportUnSyncFeature )
                        {
                        iconId = EPbk2qgn_prop_phonebook2_unsync;
                        }
                    else
                        {
                        iconId = addressValidated ?
                            EPbk2qgn_prop_locev_map : EPbk2qgn_prop_pb_no_valid_lm;
                        }
                    TPbk2IconId pbkIconId(TUid::Uid(KPbk2UID3),iconId);
                    uiField->LoadBitmapToFieldL(pbkIconId); 
                    }
                    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 && AreAllFieldsEmptyL()))
                {
                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
                        {
                        iExitRecord.Clear( EExitOrdered );
                        }
                    }
                }
            }
       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;

    // The exit callback must be invoked only once when editor dlg is exiting.
    if ( (iParams.iActiveView == TPbk2ContactEditorParams::EEditorView || 
            iAddressViewStandalone) && iParams.iExitCallback )
        {
        okToExit = iParams.iExitCallback->OkToExitL( aCommandId );
        }
    
    // If exit callback returned EFalse, the exit is cancelled
    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();
        }
    }

// --------------------------------------------------------------------------
// CPbk2ContactEditorDlgImpl::IsUnicodeL
// --------------------------------------------------------------------------
//    
TBool CPbk2ContactEditorDlgImpl::IsUnicodeL( const TDesC& aText )
    {
    if ( !iConverter )
        {
        iConverter = CCnvCharacterSetConverter::NewLC();
        CleanupStack::Pop();
        RFs& fs = Phonebook2::Pbk2AppUi()->
                ApplicationServices().ContactManager().FsSession();
        iConverter->PrepareToConvertToOrFromL( KCharacterSetIdentifierSms7Bit, fs );
        }
    
    TBool isUnicode( EFalse );
    TInt unconvertedCount(0);
    HBufC8* convertedText = HBufC8::NewLC( aText.Length()*KTwoBytes );
    TPtr8 convertedTextPtr = convertedText->Des(); 

    iConverter->ConvertFromUnicode( convertedTextPtr, aText, unconvertedCount );

    // If any characters were not converted or if the converted text is longer
    // than the original the text must be unicode
    if( unconvertedCount > 0 ||
        aText.Length() < convertedText->Length() )
        {
        isUnicode = ETrue;
        }

    CleanupStack::PopAndDestroy( convertedText );
    return isUnicode;
    }

// --------------------------------------------------------------------------
// CPbk2ContactEditorDlgImpl::IsCheckPointEvent
// --------------------------------------------------------------------------
//    
TBool CPbk2ContactEditorDlgImpl::IsCheckPointEvent(
        const TKeyEvent& aKeyEvent, TEventCode aType )
    {
    TBool check = EFalse;
    if ( EEventKeyDown == aType )
        {
        // Don't handle 'EStdKeyBackspace', 'EStdKeyHash' and those between 
        // 'EStdKeyPrintScreen' and 'EStdKeyScrollLock'. 
        // If the definition of standard scancode is changed, the scope here needs to 
        // be examined again.
        if ( ( EStdKeyPrintScreen > aKeyEvent.iScanCode || EStdKeyScrollLock < aKeyEvent.iScanCode ) &&
                EStdKeyBackspace != aKeyEvent.iScanCode &&
                EStdKeyHash != aKeyEvent.iScanCode )
            {
            check = ETrue;
            }
        }
    else if ( EEventKey == aType && EStdKeyNull == aKeyEvent.iScanCode )
        {
        check = ETrue;
        }
    
    return check;
    }

// --------------------------------------------------------------------------
// CPbk2ContactEditorDlgImpl::CheckCurrentFieldTextL
// --------------------------------------------------------------------------
//    
void CPbk2ContactEditorDlgImpl::CheckCurrentFieldTextL( 
        CPbk2ContactEditorArrayItem* aCurrentField,
        const TKeyEvent& aKeyEvent, 
        TEventCode aType )
    {
    MPbk2ContactEditorField* editorField = aCurrentField->ContactEditorField();
    if ( editorField )
        {
        MVPbkStoreContactField& contactField = editorField->ContactField();
        TVPbkFieldStorageType dataType = contactField.FieldData().DataType();
        
        if ( EVPbkFieldStorageTypeText == dataType )
            {
            const MVPbkContactFieldTextData& textData = 
                MVPbkContactFieldTextData::Cast(contactField.FieldData());
            TInt maxSize = textData.MaxLength();
            
            if ( KVPbkUnlimitedFieldLength != maxSize &&
                    IsCheckPointEvent( aKeyEvent, aType ) )
                {
                CEikEdwin* ctrl = editorField->Control();
                HBufC* textBuf = ctrl->GetTextInHBufL();
                
                if ( textBuf )
                    {
                    CleanupStack::PushL( textBuf );
                    TInt maxLen = maxSize;
                    if ( IsUnicodeL( *textBuf ) )
                        {
                        maxLen = maxSize / KTwoBytes - KExtraByte;
                        }
                    if ( ctrl->MaxLength() != maxLen && textBuf->Length() <= maxLen )
                        {
                        ctrl->SetMaxLength( maxLen );
                        }
                    CleanupStack::PopAndDestroy( textBuf );
                    }
                }
            }
        }
    }

// --------------------------------------------------------------------------
// CPbk2ContactEditorDlgImpl::HandleLosingForeground
// --------------------------------------------------------------------------
//
void CPbk2ContactEditorDlgImpl::HandleLosingForeground() 
    {
    //Fix for ou1cimx1#308012
    iEditorStrategy.StopQuery();            
    }

// --------------------------------------------------------------------------
// CPbk2ContactEditorDlgImpl::HandleGainingForeground
// --------------------------------------------------------------------------
//
void CPbk2ContactEditorDlgImpl::HandleGainingForeground() 
    {
    /*
     * iAppServices is provided to enable editor use outside from pbk2 context
     * no need to disable startup monitor in that case
     */
    if( !iAppServices )
        {
        MPbk2AppUi* pbk2AppUI = NULL;
        pbk2AppUI = Phonebook2::Pbk2AppUi();
        
        if ( pbk2AppUI && pbk2AppUI->Pbk2StartupMonitor() )
            {
            TAny* extension = pbk2AppUI->Pbk2StartupMonitor()
                    ->StartupMonitorExtension( KPbk2StartupMonitorExtensionUid );
    
            if( extension )
                {
                MPbk2StartupMonitorExtension* startupMonitorExtension =
                        static_cast<MPbk2StartupMonitorExtension*>( extension );
    
                if( startupMonitorExtension )
                    {
                    startupMonitorExtension->DisableMonitoring();
                    }
                }
            }
        }
    }

// --------------------------------------------------------------------------
// CPbk2ContactEditorDlgImpl::RestorePrevNaviDecoratorL
// --------------------------------------------------------------------------
//
void CPbk2ContactEditorDlgImpl::RestorePrevNaviDecoratorL() 
    {
    if ( iNaviContainer && iPrevNaviDecorator ) 
        {                                  
        iNaviContainer->PushL(*iPrevNaviDecorator);        
        }
    }

// --------------------------------------------------------------------------
// CPbk2ContactEditorDlgImpl::RestoreStatusPaneL
// --------------------------------------------------------------------------
//
void CPbk2ContactEditorDlgImpl::RestoreStatusPaneL() 
    {    
    //Restore StatusPane & Title    
    if ( iCurrentstatuspane )
        {
        CEikStatusPane* statusPane = iAvkonAppUi->StatusPane();
        
        if (statusPane)
            {
            statusPane->SwitchLayoutL( iCurrentstatuspane );            
            }            
        }
    // Restore the titlepane text
    if (iTitlePane && iStoredTitlePaneText)
        {    
        iTitlePane->SetTextL(*iStoredTitlePaneText);
        }
    
    // Reset title pane picture
    if( iTitlePane )
        {
        iTitlePane->SetSmallPicture( NULL, NULL, EFalse );
        }        
    }
   

// End of File