Seite 1 von 1

Fehler im Code

Verfasst: 25.09.2013 13:47
von dietmar
Hallo alle miteinander,

ich hab mir mit dem Formdesigner drei Fenster erstellt, diese verbinde ich in einer Datei zu dem untenstehenden Code, ich möchte in Fenster in dem es mehrer Buttons gibt. Wird einer der Knöpfe gedrückt soll sich ein Fenster öffnen. Die Fenster zwei und drei bekommen unterschiedliche Nummern, solange ich diese gleichzeitig geöffnet habe.
Mein Problem ist das wenn ich Fenster zwei öffne und schließe und anschließend Fenster drei öffne bekommt es die selbe Nummer zugewiesen wie Fenster zwei. Füge ich ein window_x = 0 hinter closeWindow(Window_x) geht es auch wieder.

Code: Alles auswählen

Global Window_1, Window_2, Window_3

Global Button_0, Button_1

Procedure OpenWindow_1(x = 0, y = 0, width = 600, height = 400)
  Window_1 = OpenWindow(#PB_Any, x, y, width, height, "Fenster_1", #PB_Window_SystemMenu)
  Button_0 = ButtonGadget(#PB_Any, 20, 10, 100, 25, "Fenster_2")
  Button_1 = ButtonGadget(#PB_Any, 20, 50, 100, 25, "Fenster_3")
EndProcedure

Procedure OpenWindow_2(x = 0, y = 0, width = 600, height = 400)
  Window_2 = OpenWindow(#PB_Any, x, y, width, height, "Fenster_2", #PB_Window_SystemMenu)
EndProcedure

Procedure OpenWindow_3(x = 0, y = 0, width = 600, height = 400)
  Window_3 = OpenWindow(#PB_Any, x, y, width, height, "Fenster_3", #PB_Window_SystemMenu)
EndProcedure

openwindow_1()

Procedure Hauptschleife (Event)
  Debug "Fenster 1: " + Window_1
  Debug "Fenster 2: " + Window_2
  Debug "Fenster 3: " + Window_3
  
  
  Select EventWindow()
    Case Window_1
      Select event  
        Case #PB_Event_Gadget
          Select EventGadget()
            Case Button_0
              OpenWindow_2()
            Case Button_1
              OpenWindow_3()
          EndSelect
        Case #PB_Event_CloseWindow
          CloseWindow(Window_1)
          window_1 = 0
          Exit = #True
      EndSelect
    Case Window_2
      Select event  
        Case #PB_Event_CloseWindow
          
          CloseWindow(Window_2)
      EndSelect
    Case Window_3
      Select event  
        Case #PB_Event_CloseWindow
          CloseWindow(Window_3)
      EndSelect
  EndSelect
  ProcedureReturn Exit
EndProcedure

Exit = #False

Repeat
  Exit = Hauptschleife(WaitWindowEvent())
Until Exit = #True

End
Danke und Gruß
Dietmar

Re: Fehler im Code

Verfasst: 25.09.2013 14:06
von ts-soft
Das einzige Problem was ich sehe, was auch im Bug-Thread angesprochen wurde, beim Button-Klick wird ein neues Fenster
geöffnet, das die globale Variable des noch geöffneten Fensters überschreibt, für dieses Fenster steht keine ID mehr zur Verfügung und es reagiert deshalb im Event-Loop auch nicht mehr.
Korrigierter Code:

Code: Alles auswählen

Global Window_1, Window_2, Window_3

Global Button_0, Button_1

Procedure OpenWindow_1(x = 0, y = 0, width = 600, height = 400)
  Window_1 = OpenWindow(#PB_Any, x, y, width, height, "Fenster_1", #PB_Window_SystemMenu)
  Button_0 = ButtonGadget(#PB_Any, 20, 10, 100, 25, "Fenster_2")
  Button_1 = ButtonGadget(#PB_Any, 20, 50, 100, 25, "Fenster_3")
EndProcedure

Procedure OpenWindow_2(x = 0, y = 0, width = 600, height = 400)
  Window_2 = OpenWindow(#PB_Any, x, y, width, height, "Fenster_2", #PB_Window_SystemMenu)
EndProcedure

Procedure OpenWindow_3(x = 0, y = 0, width = 600, height = 400)
  Window_3 = OpenWindow(#PB_Any, x, y, width, height, "Fenster_3", #PB_Window_SystemMenu)
EndProcedure

openwindow_1()

Procedure Hauptschleife (Event)
  Debug "Fenster 1: " + Window_1
  Debug "Fenster 2: " + Window_2
  Debug "Fenster 3: " + Window_3
 
 
  Select EventWindow()
    Case Window_1
      Select event 
        Case #PB_Event_Gadget
          Select EventGadget()
            Case Button_0
              If IsWindow(Window_2)
                CloseWindow(Window_2)
              EndIf
              OpenWindow_2()
            Case Button_1
              If IsWindow(Window_3)
                CloseWindow(Window_3)
              EndIf
              OpenWindow_3()
          EndSelect
        Case #PB_Event_CloseWindow
          CloseWindow(Window_1)
          window_1 = 0
          Exit = #True
      EndSelect
    Case Window_2
      Select event 
        Case #PB_Event_CloseWindow
         
          CloseWindow(Window_2)
      EndSelect
    Case Window_3
      Select event 
        Case #PB_Event_CloseWindow
          CloseWindow(Window_3)
      EndSelect
  EndSelect
  ProcedureReturn Exit
EndProcedure

Exit = #False

Repeat
  Exit = Hauptschleife(WaitWindowEvent())
Until Exit = #True

End
Gruß
Thomas

Re: Fehler im Code

Verfasst: 25.09.2013 14:12
von STARGÅTE
Das ist logisch.

#PB_Any erzeugt/gibt eine Nummer aus einem Pool von Zahlen (in wirklichkeit Speicherpositionen der internen PB-Objektverwaltung) zurück.

Solange diese Nummer besetzt ist, wird für ein anderes Fenster eben eine neue Nummer gesucht.
Aber wenn du das Fenster 2 schießt, verliert die Nummer auch ihre gültigkeit und wird frei, sodass Fenster 3 diese nummer selbst nutzen kann, wenn es geöffnet wird.

Lösungsvorschlag:

Öffne sofort alle Fenster und lasse sie offen. Danach kannst du mit HideWindow() alle anderen Fenster verstecken.
Bei den Buttons wird dann kein OpenWindow_2() aufgerufen, sondern HideWindow(Window_2, #False).
Beim schließen der Fenster das selbe, kein Close, sondern ein HideWindow(Window_2, #True).

Re: Fehler im Code

Verfasst: 25.09.2013 14:25
von matbal
dietmar hat geschrieben:Mein Problem ist das wenn ich Fenster zwei öffne und schließe und anschließend Fenster drei öffne bekommt es die selbe Nummer zugewiesen wie Fenster zwei. Füge ich ein window_x = 0 hinter closeWindow(Window_x) geht es auch wieder.
Ich sehe kein Problem. Wenn das Fenster geschlossen ist, ist die PB-Nummer wieder frei und kann für das andere Fenster verwendet werden.

Ich habe auch mal mit dem FormDesigner und den dynamischen PB-Nummern herumgespielt. Eigentlich hatte ich nach einer Lösung gesucht, dynamische Fenster mit dem FormDesigner zu erstellen. Und es sollen alle Funktionen, die im PBF-Dateien und dem Designer möglich sind, weiter funktionieren. (Ereignis-Procedure, resizen der Gadgets).

Ich habe das Test-Programm so erweitert, daß ich die vergebenen PB-Nummer sehe. Man kann da gut sehen, daß oft die gleichen Nummern wieder verteilt werden (4 bis 5 Nummern der zuletzt geschlossenen Fenster werden bei mir meistens wieder verwendet).

Ich habe den Code (3 Dateien) als ZIP: subwin.zip

Re: Fehler im Code

Verfasst: 27.09.2013 21:53
von dietmar
Nur noch am Rande für mich zum Verständnis, bei den Gadgets verhält es sich bestimmt ähnlich. Diese bekommen innerhalb des Fensteraufrufs eine unterschiedliche Nummer? Es können aber in unterschiedlichen Fenstern die gleiche Nummer für Gadgets vergeben werden, weil im zuerst das Fenster abgefragt wird und dann erst nach dem Gadget das ein Event auslöst?

Re: Fehler im Code

Verfasst: 27.09.2013 22:04
von ts-soft
Nein, die ID, eines jedem gleichem Objekttyps (siehe Hilfe), muß immer, im gesamtem Programm, eindeutig sein!

Bei statischen IDs, wird durch erneutes verwenden derselben ID, das vorherige Objekt
automatisch freigegeben, bei dynamischen IDs nicht (wäre ja auch gar nicht möglich :wink: )

Gruß
Thomas