5.5 Nachlade-Funktionen
Funktionen, die in der Dialogbeschreibung als Nachlade-Funktionen deklariert sind, müssen in C wie folgt deklariert werden:
DM_Boolean DML_default DM_CALLBACK Funktionsname
(
DM_ContentArgs *data
)
wenn die Funktion als
{export | reexport} function contentfunc Funktionsname();
im Dialogskript definiert ist, oder als
DM_Boolean DML_c DM_CALLBACK Funktionsname
(
DM_ContentArgs *data
)
wenn die Funktion als
{export | reexport} function c contentfunc Funktionsname ();
im Dialogskript definiert ist.
Der Parameter dieser Funktion ist fest vom Dialog Manager vorgegeben und kann nicht verändert werden. Diese Funktion wird immer dann aufgerufen, wenn bei dem Tablefield, das diese Funktion als Nachlade-Funktion definiert hat, in einen Bereich gescrollt worden ist, in dem kein Inhalt mehr im Dialog Manager vorhanden ist und dieser neu von der Anwendung geladen werden soll.
Zu beachten
Der Dialog Manager unterscheidet nicht, ob Attribute mit sichtbarer oder unsichtbarer Ausprägung (z.B. .content oder .userdata) in einer Funktion gesetzt werden. Bei jeder Änderungen eines Feldes (entspricht einer beliebigen Attributsetzung) wird dieses Feld als initialisiert betrachtet.
Werden beispielsweise mit DM_SetVectorValue nur die .userdata eines Tablefield-Bereichs gesetzt, so gilt dieser Bereich für den Dialog Manager dennoch als initialisiert und es wird für diesen Bereich keine Nachlade-Funktion mehr aufgerufen.
Beispiel
Im Dialog ist eine Nachlade-Funktion wie folgt definiert:
!! Füllt das Tablefield beim Scrollen auf,
!! wenn es notwendig wird
function contentfunc CONTENT();
Diese Funktion wird dann an ein Tablefield wie folgt gebunden:
child tablefield T1
{
.visible true;
.xauto 0;
.xleft 1;
.xright 1;
.yauto 0;
.ytop 0;
.ybottom 1;
.posraster true;
.contentfunc CONTENT;
.edittext null;
.selection[sel_row] true;
.selection[sel_header] false;
.selection[sel_single] false;
.colcount 3;
.rowcount 30;
.rowheadshadow true;
.rowheader 1;
.colfirst 1;
.rowfirst 2;
.colwidth[0] 12;
.rowheight[0] 1;
.rowlinewidth[0] 1;
.rowlinewidth[1] 3;
.sensitive[1,1] false;
.content[1,1] "Name";
.sensitive[1,2] false;
.content[1,2] "Vorname";
.sensitive[1,3] false;
.content[1,3] "Wohnort";
.xraster 10;
.yraster 16;
}
Die Realisierung der Funktion in C sieht dann wie folgt aus:
/*
** Funktion zum dynamischen Auffuellen des Tablefields
** beim Scrollen, wenn Zeilen im Tablefield erreicht werden,
** die noch nicht gefuellt sind.
*/
void DML_default DM_CALLBACK CONTENT __1(
(DM_ContentArgs *, args))
{
int i;
int spos;
int vpos;
int length;
FILE *f ;
char ** strvec;
char * buffer;
char * start;
char * end;
DM_VectorValue vector;
DM_Value startIdx;
DM_Value endIdx;
/*
** Öffnen der Datei, aus der der Inhalt des Tablefields
** gelesen werden soll
*/
if (!(f = fopen("bsp.dat","r")))
{
DM_TraceMessage("Cannot open In-File", DMF_LogFile);
return;
}
/*
** Allokierung von Speicher, damit die gelesenen Zeilen
** vor der Zuweisung an das Objekt zwischengespeichert
** werden können. Dazu werden die DM_-Funktionen genutzt.
*/
strvec = (char **) DM_Malloc ( (CONT_ROWS * COLUMNS)
* sizeof (char*) );
buffer = (char *) DM_Malloc (STR_LEN * sizeof (char) );
/*
** erste Zelle des Tablefields, die gefuellt wird
*/
startIdx.type = DT_index;
startIdx.value.index.first = args->loadfirst - 1;
startIdx.value.index.second = 1;
/*
** letzte Zelle des Tablefields, die gefuellt wird
*/
endIdx.type = DT_index;
endIdx.value.index.first = startIdx.value.index.first +
(ushort) CONT_ROWS - 1;
endIdx.value.index.second = COLUMNS;
vector.type = DT_string;
vector.vector.stringPtr = strvec;
spos = 0;
vpos = 0;
/*
** Einlesen der Datei in den Zwischenspeicher.
** Dabei wird nach jedem Leerzeichen ein neues Element
** im Tablefield angefangen
*/
while ( !feof(f) && (spos++ < CONT_ROWS) )
{
if (fgets(buffer ,STR_LEN-1, f))
{
i = 0;
end = buffer;
while (*end && isspace(*end))
end++;
while (*end && (i++ < COLUMNS))
{
start = end;
length = 1;
while (*end && !isspace(*end))
{
length++;
end++;
}
if (*end)
*end++ = '\0';
strvec[vpos]=(char *) DM_Malloc( (lenght+1) *
sizeof(char));
strcpy(strvec[vpos],start);
vpos++;
while(*end && isspace(*end))
end++;
}
while (i++ < COLUMNS)
{
strvec[vpos] = (char *) DM_Malloc(sizeof(char));
strvec[vpos++]="\0";
}
}
}
/*
** Setzen der Anzahl der gültigen Einträge in dem Vektor
*/
vector.count = (ushort) vpos;
/*
** Zuweisen des aufgebauten Vektors an das Tablefield
*/
DM_SetVectorValue(args->object, AT_field,
&startIdx, &endIdx, &vector, 0);
/*
** Freigeben des Speichers, der in dieser Funktion
** allokiert worden ist.
*/
while (--vpos >= 0 )
DM_Free(strvec[vpos]);
DM_Free(strvec);
DM_Free(buffer);
}