19. Objekte individualisierenEs gibt Situationen, in denen es nötig ist, dass ein Objekt neben den vom System vorgegebenen Daten weitere Informationen speichern muss. Ein einfaches Beispiel ist ein Canvas-Objekt, dass entweder einen Kreis oder ein Quadrat zeichnen soll. Sie können die Information, ob ein Kreis oder ein Quadrat gezeichnet werden soll, natürlich in einer globalen Variablen speichern. Das ist aber nicht nur schlechter Stil sondern wird bei mehreren solchen Objekte auch schnell sehr unübersichtlich und damit fehleranfällig.Die bessere Lösung ist, die Information im Objekt selber zu speichern. R-BASIC bietet Ihnen für diese Situation die Instancevariable privData. PrivData nimmt eine Strukturvariable beliebigen Typs auf und speichert sie im Objekt selbst. Hier können Sie z.B. ablegen, ob ein Kreis oder ein Quadrat gezeichnet werden soll. Außerdem können Sie - wenn Sie wollen - die Größe, die Farbe und beliebige weitere Informationen speichern.
Fortgeschrittene Programmierer können in einigen Situationen den Bedarf haben, dass sie eine Routine erst dann aufrufen wollen, wenn der aktuelle Actionhandler vollständig abgearbeitet ist. Typische Beispiele sind hier der OnPrint Handler (bei dem man das Screen-Objekt nicht ändern darf) oder ein OnMouse~ bzw. der OnKeyPressed Handler (die meist zeitkritisch sind). R-BASIC löst dieses Problem, indem man für Objekte eigene, private ("custom") Handler definieren kann. Actionhandler unterbrechen sich niemals, sondern werden immer nacheinander abgearbeitet. Der Aufruf eines solchen Handlers führt also dazu, dass die aktuelle Routine (genauer: der komplette aktuell laufende Handler) zuerst vollständig abgearbeitet wird bevor der neue Handler ausgeführt wird. Um einen Custom Handler für ein Objekt festzulegen verwenden Sie die Instancevariable CustomHandler. Custom Handler müssen als CustomAction deklariert sein. Um einen Custom Handler aufzurufen, verwenden Sie die Methode CustomApply.
PrivDataPrivData ist für alle Klassen definiert. Sie nimmt eine einzelne Strukturvariable (also maximal 3500 Bytes) auf. Diese Instancevariable ist zuweisungskompatibel mit jeder Art von Struktur, es wird weder eine Typ- noch eine Größenprüfung ausgeführt. Es ist daher vernünftig beim Schreiben und beim Lesen der Daten den gleichen Struktur-Datentyp zu verwenden.
Achtung! PrivData kann nicht im UI Code belegt werden! Wenn Sie wollen, dass privData am Programmstart mit vorgegebenen Werten belegt wird, müssen Sie das im OnStartup Handler tun. Beispiel: Ein Canvas-Objekt soll einen Kreis oder ein Quadrat in einer vorgegebenen Farbe zeichnen. Wir benötigen: - einen Strukturtyp, der die Informationen enthält,Der Strukturtyp sei folgendermaßen definiert: |
STRUCT ImgData isCircle as Integer color as Integer End Struct |
|
Zum Belegen der Instancewerte dient die folgende Routine. Die zweite Routine (SetCanvasToRect) ist hier nicht aufgeführt. |
SUB SetCanvasToCircle(col as Integer) DIM pd AS ImgData pd.isCircle = TRUE pd.color = col DemoCanvas.privData = pd, SIZEOF(pd) DemoCanvas.Dirty ' Neudarstellung auslösen End Sub |
|
Das Canvas-Objekt sei wie folgt definiert. Beachten Sie, dass wir privData nicht definieren brauchen, es ist für alle Objekte automatisch verfügbar. |
CANVAS DemoCanvas OnDraw = DrawFigure fixedSize = 70, 70 End Object |
|
Unser Application-Objket benötigt einen OnStartup Handler. |
Application DemoApplication Children = DemoPrimary OnStartup = AppStartup End OBJECT |
|
Schließlich benötigen wir noch den OnDraw-Handler, der die privData-Werte ausliest und verwendet, sowie den OnStartup Handler für das Application-Objekt. |
DRAWACTION DrawFigure
DIM priv as ImgData
priv = sender.privData
INK priv.color
IF priv.isCircle THEN
FillEllipse 10, 10, 60, 60
ELSE
FillRect 10, 10, 60, 60
END IF
End Action
|
SYSTEMACTION AppStartup SetCanvasToCircle(LIGHT_RED) END ACTION |
CustomHandlerCustomHandler enthält den Namen des Actionhandlers, der mit der Methode CustomApply aufgerufen werden soll.Syntax UI- Code: CustomHandler = <Handler> Schreiben: <obj>.CustomHandler = <Handler> Ein Custom Handler muss als CustomAction deklariert sein:
CustomApplyDie Methode CustomApply ruft den CustomHandler eines Objekts auf. Ihr wird ein Integer-Wert übergeben, der an den Handler weitergereicht wird.Syntax: <obj>.CustomApply actionData actionData: Integerwert, der an CustomHandler übergeben wird. Beispiel (einfach, deswegen nicht sehr sinnvoll): Ein Button mit einem ActionHandler und Primary mit einem CustomHandler. |
BUTTON MyButton Caption$ "Drück mich!" ActionHandler = PressHandler End Object BUTTON MyPrimary CustomHandler = CHandler End Object |
|
Der Actionhandler: |
ButtonAction PressHandler Print "Text 1" MyPrimary.CustomApply 1 Print "Text 2" MyPrimary.CustomApply -7 Print "Text 3" End Action |
|
Der CustomHandler wird erst ausgeführt, wenn der ActionHandler fertig ist |
CustomAction CHandler DIM i IF actionData < 0 THEN i = RED : ELSE i = BLUE Print Ink i;"DATA = ";actionData End Action |
|
Wenn der Nutzer den Button drückt erscheint folgendes: |
Text 1 Text 2 Text 3 DATA = 1 DATA =-7 |
^ |