Parent-Owner-Beziehung

Aus Wiki des Deutschsprachige Xbaseentwickler e. V.
Zur Navigation springen Zur Suche springen


Beschreibung

Die Parent-Owner-Beziehung zwischen Xbase-Parts hat Einfluss auf ihre Darstellung und Ihr Verhalten.

Werden weder Parent, noch Owner angegeben, greifen bestimmte Unterlassungswerte:

Beginnen wir mit einem XbpDialg(). Wird bei Ausführen der Methode :new() kein Wert für <oParent> angegeben, so verwendet das Laufzeitsystem den Rückgabewert der Funktion SetAppWindow() als Parent.

Wird kein <oOwner> angegeben, so wird der Wert von <oParent> verwendet.

Dieses Verhalten zieht sich durch alle Xbase-Parts, die eine Zuweisung von Parent und Owner ermöglichen.

Von den Standard-Einstellungen her sind Parent und Owner identisch.

Es kann aber auch Gründe geben, von dieser Aufteilung abzuweichen. Im Normalfall kommen zwei Objekte als Parent bzw. Owner in Frage:

- Der Desktop (Rückgabewert von AppDesktop())
- das Anwendungsfenster (Rückgabewert von SetAppWindow()

Was sich so einfach anhört, hat gewisse Auswirkungen auf das Erscheinungsbild der Fenster.


Beispiel

#INCLUDE "AppEvent.CH"
#INCLUDE "NLS.CH"
#INCLUDE "Xbp.CH"

FUNCTION Main()
  Local mp1, mp2
  Local nEvent
  Local oXbp

  GenerateMenu()
  SetAppFocus(SetAppWindow())

  nEvent := xbe_None
  mp1 := mp2 := oXbp := nEvent
  WHILE nEvent <> xbeP_Close
     nEvent := AppEvent(@mp1, @mp2, @oXbp)
     oXbp:handleEvent(nEvent, mp1, mp2)
  END

RETURN (.T.)

FUNCTION MakeMyWin(oParent, oOwner, cParentName, cOwnerName)
  Local aPos, aSize
  Local cTitle
  Local oXbp

  aPos := {500, 500}
  aSize := {450, 150}
  oXbp := XbpDialog():new(oParent, oOwner, aPos, aSize)
  cTitle := "Parent: " + cParentName + "; Owner: " + cOwnerName
  oXbp:title := cTitle
  oXbp:sysMenu := .T.
  oXbp:minButton := .T.
  oXbp:maxButton := .T.
  oXbp:create()

RETURN (.T.)

FUNCTION GenerateMenu()
  Local oBar, oMenu, oSub, oRoot, oDesk

  oRoot := RootWindow()
  oDesk := AppDesktop()
  oBar := oRoot:menuBar()

  oSub := XbpMenu():new(oBar):create()
  oSub:title := "~Datei"
  oSub:addItem({"~Ende", {|| Eval(RootWindow():close)}})
  oBar:addItem({oSub, NIL})

  oSub := XbpMenu():new(oBar):create()
  oSub:title := "~Verwandschaften"
  oSub:addItem({"~App/App",      {|| MakeMyWin(oRoot, oRoot, "Application", "Application")}})
  oSub:addItem({"App/~Desk",     {|| MakeMyWin(oRoot, oDesk, "Application", "Desktop")}})
  oSub:addItem({"D~esk/App",     {|| MakeMyWin(oDesk, oRoot, "Desktop", "Application")}})
  oSub:addItem({"De~sk/Desk",    {|| MakeMyWin(oDesk, oDesk, "Desktop", "Desktop")}})
  oBar:addItem({oSub, NIL})

RETURN (.T.)

FUNCTION CleanUpAfter()
RETURN (.T.)

FUNCTION GetProgramTitle()
  Local cTitle
  cTitle := "Parent-Owner-Beziehung, endlich offengelegt"
RETURN (cTitle)

FUNCTION WinManKill()
RETURN (.T.)

FUNCTION AppSys()
  Local aSize, oDlg, aPos[2], aSizeNew[2], nI

  SetLocale(NLS_ICURRENCYEURO, "1")
  SET CHARSET TO ANSI
  SET DATE GERMAN
  SET CENTURY ON

  aSize := AppDesktop():currentSize()
  FOR nI := 1 TO 2
     aSizeNew[nI] := Int(aSize[nI] * 0.6)
  NEXT
  IF aSizeNew[1] < 800
     aSizeNew[1] := 800
  ENDIF
  IF aSizeNew[2] < 600
     aSizeNew[2] := 600
  ENDIF
  aPos[1] := Int((aSize[1] - aSizeNew[1]) / 2)
  aPos[2] := Int((aSize[2] - aSizeNew[2]) / 2)
  oDlg := XbpDialog():new(AppDesktop(), AppDesktop(), aPos, aSizeNew, , .F.)
  oDlg:sysmenu := .T.
  oDlg:hideButton := .T.
  oDlg:taskList := .T.
  oDlg:close := {|| WinManKill(), _QUIT()}
  oDlg:title := ""
  oDlg:icon := 2001
  oDlg:create()
  RootWindow(oDlg)
  oDlg:setTitle(GetProgramTitle())
  oDlg:drawingArea:scrollBars := XBP_SCROLLBAR_VERT
  oDlg:show()

  SetAppWindow(oDlg)

RETURN (.T.)

FUNCTION RootWindow(oDlg)
  Static oStatic
  IF oDlg <> NIL
     oStatic := oDlg
  ENDIF
  IF oStatic = NIL
     ConfirmBox(, "Fehler", "Programm nicht richtig geladen", XBPMB_CRITICAL, XBPMB_OK)
     QUIT
  ENDIF
RETURN (oStatic)

Diese Beispiel erlaubt es, vier Fenster mit gleichen Koordinaten, aber unterschiedlichen Angaben zu Parent und Owner (vier mögliche Kombinationen) zu erzeugen.

So beziehen sich die Positionierunsangaben (<aPos>) immer auf den Parent, und auch das Erscheinungsbild ändert sich, wenn der Parent nicht mehr das Anwendungsfenster, sondern der Desktop ist.


Hinweis

Wird - wie der Standard vorsieht - das Anwendungsfenster als Parent verwendet, kann man alle Xbase-Parts über ein rekursives Abarbeiten der childList() ermitteln. Das funktioniert nicht mehr, wenn Xbase-Parts den Desktop als Parent verwenden. In diesem Fall muss zusätzlich die childList des Desktops abgearbeitet werden, um alle Xbase-Parts zu ermitteln.