TN026: Routine di DDV e DDX

[!NOTA]

La seguente nota tecnica non è stata aggiornata da quando è stata inclusa nella documentazione online.Di conseguenza, alcune procedure e argomenti potrebbero non essere aggiornati o errati.Per le informazioni più recenti, è consigliabile cercare l'argomento di interesse nell'indice della documentazione online.

Questa nota viene descritta l'architettura di (DDV) di scambio di dati della finestra di dialogo (DDX) e di convalida dei dati della finestra di dialogo.Viene descritto come scrivere una routine di DDV_ o di DDX_ e come è possibile estendere ClassWizard per utilizzare le routine.

Tutte le funzioni di dati della finestra di dialogo vengono effettuate con il codice C++.Non esistono risorse speciali macro o magiche.Il fulcro del meccanismo è una funzione virtuale sottoposta a override in ogni classe della finestra di dialogo con lo scambio di dati e la convalida della finestra di dialogo.Si trova sempre nel seguente formato:

void CMyDialog::DoDataExchange(CDataExchange* pDX)
{
    CDialog::DoDataExchange(pDX);    // call base class

    //{{AFX_DATA_MAP(CMyDialog)
        <data_exchange_function_call>
        <data_validation_function_call>
    //}}AFX_DATA_MAP
}

I commenti speciali di AFX di formato consentono di ClassWizard individuare e modificare il codice nella funzione.Il codice che non è compatibile con ClassWizard deve essere posizionato fuori dei commenti speciali di formato.

Nell'esempio precedente, <data_exchange_function_call> è nel form:

    DDX_Custom(pDX, nIDC, field);

e <data_validation_function_call> è facoltativo e si trova nel form:

    DDV_Custom(pDX, field, ...);

Più di una coppia di DDX_/DDV_ può essere inclusa in ogni funzione di DoDataExchange.

Vedere "afxdd_.h" per un elenco di tutte le routine di scambio di dati della finestra di dialogo e delle routine di convalida dei dati della finestra di dialogo disponibili in MFC.

I dati della finestra di dialogo sono solo quando: dati dei membri della classe CMyDialog.Non viene archiviata in uno struct o in un comportamento simile.

Note

Sebbene si chiameranno i dati "della finestra di dialogo," tutte le funzionalità disponibili in qualsiasi classe derivata da CWnd e non sono limitate alle finestre di dialogo.

I valori iniziali di dati sono impostati nel costruttore C++ standard, generalmente in un blocco con //{{AFX_DATA_INIT e commenti di //}}AFX_DATA_INIT.

CWnd::UpdateData è l'operazione che esegue l'inizializzazione e la gestione degli errori per racchiudere la chiamata a DoDataExchange.

È possibile chiamare CWnd::UpdateData in qualsiasi momento per eseguire lo scambio di dati e la convalida.Per impostazione predefinita UpdateDataTRUE () viene chiamato il gestore predefinito di CDialog::OnOK e in UpdateDataFALSE () viene chiamato in CDialog::OnInitDialogpredefinito.

La routine di DDV_ deve seguire immediatamente la routine di DDX_ per tale campo.

Funzionamento?

Non è necessario comprendere le seguenti per contenere i dati della finestra di dialogo.Tuttavia, capire il funzionamento automaticamente possono consentire di scrivere una routine di convalida o di scambio.

La funzione membro di DoDataExchange è molto simile alla funzione membro di Serialize - è responsabile di ottenere o impostare dei dati a/da un form esterno (in questo caso controlli in una finestra di dialogo) da/verso i dati dei membri della classe.Il parametro di pDX è il contesto per eseguire lo scambio di dati ed è simile al parametro di CArchive a CObject::Serialize.pDX (un oggetto di CDataExchange ) dispone di una direzione del flag è molto simile CArchive ha un flag di direzione:

  • Se !m_bSaveAndValidate, quindi carica lo stato di dati nei controlli.

  • Se m_bSaveAndValidate, quindi impostando lo stato di dati dai controlli.

La convalida si verifica solo quando m_bSaveAndValidate è impostato su.Il valore di m_bSaveAndValidate è determinato dal parametro di BOOL a CWnd::UpdateData.

Esistono altri tre membri interessanti di CDataExchange :

  • m_pDlgWnd: La finestra in genere una finestra di dialogo) che contiene i controlli.Ciò consente di evitare i chiamanti di DDX_ e di DDV_ che le funzioni globali devono da questo passa" a ogni routine di DDX/DDV.

  • PrepareCtrle PrepareEditCtrl: Rende un controllo finestra di dialogo per lo scambio di dati.Archivi tale manopola di comando per impostare lo stato attivo se la convalida non riesce.PrepareCtrl viene utilizzato per i controlli di nonedit e PrepareEditCtrl viene utilizzato per i controlli di modifica.

  • Errore: Chiamata dopo allevato una finestra di messaggio che avvisa l'utente all'errore di input.Questa procedura ripristinerà lo stato attivo all'ultimo controllo (l'ultima chiamata a PrepareCtrl/PrepareEditCtrl) e genererà un'eccezione.Questa funzione membro può essere chiamata sia dalle routine di DDV_ di DDX_.

Estensioni dell'utente

Esistono diversi modi per estendere il meccanismo di impostazione predefinita DDX/DDV.È possibile:

  • Aggiungere nuovi tipi di dati.

    CTime
    
  • Aggiungere nuove procedure di scambio (DDX_???).

    void PASCAL DDX_Time(CDataExchange* pDX, int nIDC, CTime& tm);
    
  • Aggiungere nuove routine di convalida (DDV_???).

    void PASCAL DDV_TimeFuture(CDataExchange* pDX, CTime tm, BOOL bFuture);
    // make sure time is in the future or past
    
  • Passare le espressioni arbitrarie alle procedure di convalida.

    DDV_MinMax(pDX, age, 0, m_maxAge);
    

    [!NOTA]

    Tali espressioni arbitrarie non possono essere modificate da ClassWizard e pertanto non devono essere spostato fuori dei commenti speciali di formato (// {{AFX_DATA_MAP (CMyClass).

Scegliere la funzione membro DoDialogExchange includere istruzioni condizionali o qualsiasi altra istruzione validi C++ con chiamate di funzione alternate di convalida e di scambio.

//{{AFX_DATA_MAP(CMyClass)
DDX_Check(pDX, IDC_SEX, m_bFemale);
DDX_Text(pDX, IDC_EDIT1, m_age);
//}}AFX_DATA_MAP
if (m_bFemale)
    DDV_MinMax(pDX, age, 0, m_maxFemaleAge);
else
    DDV_MinMax(pDX, age, 0, m_maxMaleAge);

[!NOTA]

Come illustrato in precedenza, tale codice non può essere modificato da ClassWizard e deve essere utilizzato solo da commenti speciali di formato.

Supporto di ClassWizard

ClassWizard supporta un sottoinsieme delle personalizzazioni di DDX/DDV consentendo a integriate le routine di DDV_ e di DDX_ nell'interfaccia utente di ClassWizard.Questo scopo è costato utile solo se si intende riutilizzare le routine specifiche di DDV e DDX in un progetto o in più progetti.

Per eseguire questa operazione, le voci specifiche vengono effettuate in DDX.CLW (versioni precedenti di Visual C++ archiviare tali informazioni in APSTUDIO.INI) o nel file .CLW del progetto.Le voci speciali possono essere inserite nella sezione [] informazioni generali del file di .CLW del progetto o nella sezione [] ExtraDDX del file di DDX.CLW in \ programmi \ Microsoft Visual Studio \ Visual C++ directory \ bin.Potrebbe essere necessario creare il file di DDX.CLW se non esiste già.Se si intende utilizzare le routine personalizzate DDX_/DDV_ solo in un determinato progetto, aggiungere voci alla sezione [] informazioni generali del file di progetto .CLW anziché.Se si intende utilizzare le routine in molti progetti, aggiungere voci alla sezione [] ExtraDDX di DDX.CLW.

Lo schema generale di queste voci speciali è:

ExtraDDXCount=n

dove n è il numero di ExtraDDX?righe da utilizzare

ExtraDDX?=<keys>;<vb-keys>; <prompt>; <type>; <initValue>; <DDX_Proc>
[;<DDV_Proc>; <prompt1>; <arg1>; [<prompt2>; <fmt2>]]

dove?è un numero 1 – indica n quali DDX i tipi nell'elenco che viene definito.

Ogni campo è delimitato da "; ".I campi e il relativo scopo sono descritti di seguito.

  • <keys>
    = l'elenco dei singoli caratteri che indicano per il quale la finestra di dialogo controlla questo tipo di variabile è consentito.

    E = modifica

    C = casella di controllo a due stati

    c = casella di controllo a tre stati

    R = primo pulsante di opzione in un gruppo

    " = Casella di riepilogo nonsorted

    la pre-elaborazione = stato ordinato la casella di riepilogo

    M. = casella combinata con l'elemento di modifica)

    N = elenco nonsorted di trascinamento

    n = elenco ordinato di trascinamento

    1 = se inserimento DDX verrà aggiunto all'inizio dell'elenco (impostazione predefinita viene aggiunto alla coda) che viene utilizzato in genere per le routine DDX che contengono la proprietà del controllo".

  • <vb-keys>
    Questo campo viene utilizzato solo nel prodotto a 16 bit per i controlli di VBX (i controlli di VBX non supportati nel prodotto a 32 bit)

  • <prompt>
    Stringa da inserire nella casella combinata della proprietà (nessun valore)

  • <tipo>
    Selezionare l'identificatore di tipo per generare il file di intestazione.Nell'esempio precedente con DDX_Time, è impostato su CTime.

  • <vb-keys>
    Non utilizzato in questa versione e deve essere sempre vuoto

  • <initValue>
    Valore iniziale — 0 o spazio vuoto.Se è vuoto, quindi alcuna linea di inizializzazione verrà scritta in //{{sezione di AFX_DATA_INIT il file di implementazione.Una voce vuota deve essere utilizzata per gli oggetti C++ (come CString, CTimee così via, che dispongono di costruttori che garantiscono l'inizializzazione corretta.

  • <DDX_Proc>
    Singolo identificatore per la routine di DDX_.Il nome della funzione C++ deve iniziare con "DDX_", ma non include "DDX_" l'identificatore di <DDX_Proc> .Nell'esempio precedente, l'identificatore di <DDX_Proc> sarebbe tempo.Quando ClassWizard scrive la chiamata di funzione nel file di implementazione in {{sezione di AFX_DATA_MAP, aggiunge questo nome a DDX_, quindi arrivando a DDX_Time.

  • <comment>
    Commenti da visualizzare nella finestra di dialogo per la variabile con questo meccanismo DDX.Inserire tutto il testo che si desidera siano qui e in genere immettere testo che descrive l'operazione eseguita da una coppia di DDX/DDV.

  • <DDV_Proc>
    La parte di DDV voce è facoltativa.Non tutte le routine DDX hanno routine corrispondenti di DDV.Spesso, è consigliabile includere la fase di convalida come parte integrante del trasferimento.È spesso avviene quando la routine di DDV non richiede alcuni parametri, perché ClassWizard non supporta le routine di DDV senza parametri.

  • <arg>
    Singolo identificatore per la routine di DDV_.Il nome della funzione C++ deve iniziare con "DDV_", ma non include "DDX_" l'identificatore di <DDX_Proc> .

seguito da 1 o 2 argomenti di DDV:

  • <promptX>
    stringa da inserire nell'elemento di modifica (con & per la scelta rapida)

  • <fmtX>
    carattere di formato per il tipo di argomento, uno di

    d = int

    u " unsigned

    D = tempo int (ovvero long)

    U = tempo senza segno (ovvero DWORD)

    f = float

    F = doppio

    i = stringa

Vedere anche

Altre risorse

Note tecniche del numero

Note tecniche per categoria