Hallo zusammen
Ich versuche gerade mit den
api-funktionen einen Dialog zu erzeugen und.. grundsätzlich funktioniert das auch ganz gut
wenn ich die funktion DialogBox verwende, muss ich, um daten zwüschen dem Dialog und dem Formular auszutauschen, globale variablen verwenden! So wie ich verstanden habe, kann man aber, um das zu vermeiden, die funktion DialogBoxParam verwenden und einen Zeiger z.b. auf einen Record mitgeben!? In meinem programm sie es wie folgt aus:
Delphi-Quellcode:
TTestRec =
record
Test:
String;
end;
TfrmTest =
class(TForm)
private
FTestRec: TTestRec;
procedure TestDlg;
end;
procedure TfrmTest.TestDlg;
function DlgProc(hDlg: HWND; uMsg: UINT; wParam: WPARAM; lParam: LPARAM): BOOL;
stdcall;
begin
Result := True;
Case uMsg
of
WM_INITDIALOG:
begin
SetDlgItemText(hDlg, IDC_DICT_LOCATION, PChar(TTestRec(Pointer(lParam)^).Test));
end;
WM_COMMAND:
begin
case LOWORD(wParam)
of
ID_OK: EndDialog(hDlg, ID_OK);
ID_CANCEL: EndDialog(hDlg, ID_CANCEL);
end;
end;
else
Result := False;
end;
end;
begin
DialogBoxParam(hInstance, PChar('
TESTDLG'),
Handle, TFNDlgProc(@DlgProc), LPARAM(@FTestRec));
end;
Beim Starten des Dialogs wird der DialogProzedure die Nachricht WM_INITDIALOG geschickt und im lParam der Zeiger mitgegeben! Ich kann zu diesem Zeitpunkt sowohl in den record schreiben, wie auch von ihm lesen! Wenn der Benutzer seine eingaben gemacht hat und auf OK clickt sollte ich die Änderungen wieder in den record zurückschreiben können! dieser nachricht (WM_COMMAND) wird mein Zeiger natürlich nicht mehr mitgegeben
ich müsste irgendwie die möglichkeit haben den zeiger bei der WM_INITDIALOG nachricht zu speichern, damit er mir nacher noch zur Verfügung steht!? Dazu möchte ich aber keine globalen veriablen verwenden! eine lokale veriable in der prozedur TestDlg finde ich auch nicht so gut und es funktioniert auch nicht (gibt eine accessviolation)!
folgend ein ausschnitt eines c-codes von dem buch "windows 2000
api referenz":
Code:
typedef struct
{
int nEditOne;
char szEditTwo[20];
} DLGDATA, *LPDLGDATA;
LRESULT CALLBACK WndProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam )
{
static LPDLGDATA lpMem;
switch( uMsg )
{
case WM_CREATE :
lpMem = (LPDLGDATA)HeapAlloc( GetProcessHeap(),
HEAP_ZERO_MEMORY,
sizeof( DLGDATA ) );
lpMem->nEditOne = 10;
strcpy( lpMem->szEditTwo, "Edit Two" );
break;
case WM_COMMAND :
switch( LOWORD( wParam ) )
{
case IDM_TEST :
DialogBoxParam( hInst, "TestDialog", hWnd,
(DLGPROC)TestDlgProc,
(LPARAM)lpMem );
break;
}
break;
case WM_DESTROY :
if ( lpMem )
HeapFree( GetProcessHeap(), 0, lpMem );
PostQuitMessage(0);
break;
default :
return( DefWindowProc( hWnd, uMsg, wParam, lParam ) );
}
return( 0L );
}
LRESULT CALLBACK TestDlgProc( HWND hDlg, UINT uMsg,
WPARAM wParam, LPARAM lParam )
{
static LPDLGDATA lpMem;
switch( uMsg )
{
case WM_INITDIALOG :
lpMem = (LPDLGDATA)lParam;
SetDlgItemInt ( hDlg, IDC_EDIT1, lpMem->nEditOne, TRUE );
SetDlgItemText( hDlg, IDC_EDIT2, lpMem->szEditTwo );
break;
case WM_COMMAND :
switch( LOWORD( wParam ) )
{
case IDOK :
{
BOOL bTran;
lpMem->nEditOne = GetDlgItemInt( hDlg, IDC_EDIT1,
&bTran, TRUE );
GetDlgItemText( hDlg, IDC_EDIT2, lpMem->szEditTwo,
sizeof(lpMem->szEditTwo)-1 );
EndDialog( hDlg, IDOK );
}
break;
case IDCANCEL :
EndDialog( hDlg, IDCANCEL );
break;
}
break;
default :
return( FALSE );
}
return( TRUE );
}
Irgendwie kann man mit
static z.b. dem code "static LPDLGDATA lpMem;" eine lokale variable erzeugen, die aber auch beim erneuten aufruf der procedure noch den zugewiesenen wert hat!? oder was passiert da so genau? gibt es in delphi evtl. auch so etwas ähndliches oder hat jemand eine andere idee, wie man diese funktion in delphi sinnvoll einsetzten kann? ich bedanke mich für jede antwort
Grüsse dominic