Seite 1 von 1

xbpcrt und GUI

Verfasst: So, 02. Sep 2012 19:18
von saul
Hallo,
seit langem habe ich mal wieder versucht GUI Elemente in meine Programme einzubinden. Leider ist eine kopmplette Umstellung aus Zeitgründen nicht zu machen. Ich möchte mich aber gern mit GUI beschäftigen und Stück für Stück weitermachen. Nun habe ich im CRT Fenster eine Tabelle ausgeben können. Dies Beispiel habe ich aus der Xbase++ Hilfe genommen. Es funktioniert bis auf den Ausstieg.

Code: Alles auswählen

#include "Xbp.ch"
#include "Appevent.ch"
#include "Appevent.ch"
#include "Common.ch"
#include "Directry.ch"
#include "Dmlb.ch"
#include "Fileio.ch"
#include "GRA.ch"
#include "Inkey.ch"
#include "Memoedit.ch"
#include "Setcurs.ch"
#include "XBP.ch"

#pragma Library( "XppUi2.lib" )

PROCEDURE  Main
  LOCAL nEvent, mp1, mp2, oXbp, oBrowse, cField, i
  use lfz_zeit		 									// Datenbank öffnen

  // Dialogfenster versteckt erzeugen
  oXbp := GuiStdDialog( "Standard GUI Browser for DBF" )
  // Browser im Fenster erzeugen
  oBrowse := GuiBrowseDb( oXbp:drawingArea )
  // Spalten für alle Felder anfügen
  FOR i:=1 TO FCount()
    cField := FieldName( i )
    oBrowse:addColumn( FieldBlock(cField), , cField )
  NEXT
  // Der Browser füllt nach :resize() immer das Fenster aus
  oXbp:drawingArea:resize := {|mp1,mp2,obj| obj:childList()[1]:setSize(mp2) }
  oXbp:show()
  oBrowse:show()
  SetAppFocus( oBrowse )
  nEvent = 0
  DO WHILE nEvent <> xbeP_Close
    nEvent := AppEvent( @mp1, @mp2, @oXbp )
    DO CASE
      CASE nEvent == xbeP_Keyboard .AND. mp1 == xbeK_ESC
        exit
      OTHERWISE
        oXbp:handleEvent( nEvent, mp1, mp2 )
    ENDCASE
  ENDDO
  oXbp:destroy()
?"Hier bin ich wieder im CRT Fenster"
wait
RETURN

******************************************************************
* GUI Browser mit Navigations-Codeblöcken für DBF erzeugen
******************************************************************
   FUNCTION GuiBrowseDB( oParent, aPos, aSize )
      LOCAL oBrowse
      oBrowse := XbpBrowse():new( oParent,, aPos, aSize ):create()
      // Navigationscodeblöcke für den Browser
      oBrowse:skipBlock     := {|n| DbSkipper(n) }
      oBrowse:goTopBlock    := {| | DbGoTop()    }
      oBrowse:goBottomBlock := {| | DbGoBottom() }
      oBrowse:phyPosBlock   := {| | Recno()      }
      // Navigationscodeblöcke für den vertikalen Scrollbar
      oBrowse:posBlock      := {| | DbPosition()    }
      oBrowse:goPosBlock    := {|n| DbGoPosition(n) }
      oBrowse:lastPosBlock  := {| | 100             }
      oBrowse:firstPosBlock := {| | 0               }
   RETURN oBrowse


******************************************************************
* Standard Dialogfenster versteckt erzeugen
******************************************************************
   FUNCTION GuiStdDialog( cTitle )
      LOCAL oDlg
      DEFAULT cTitle TO "Standard Dialog Window"
      oDlg          := XbpDialog():new( ,,{10,10}, {500,300},, .F. )
      oDlg:icon     := 1
      oDlg:taskList := .T.
      oDlg:title    := cTitle
      oDlg:titlebar := .T.
      oDlg:create()
      oDlg:drawingArea:setFontCompoundName( "10.Helv" )
   RETURN oDlg

Gehe ich mit der ESC Taste raus, so erscheint auf dem CRT Fenster '"Weiter mit einer Taste, aber das Dialogfenster ohne den Browseteil bleibt stehen und das Programm läßt sich nur über ALT+C verlassen.
Schließe ich das GUI FEnster über das X rechts oben in der Titelzeile, so wird das GUI Fenster vollständig beseitigt und ich kann mittels einer Taste im Programm fortfahren.
Was mache ich beim Aussteig mittels ESC Taste falsch?
mfg
Wolfgang

Re: xbpcrt und GUI

Verfasst: So, 02. Sep 2012 20:52
von georg
Hallo,


so ganz kurz am Sonntag Abend:

wenn auf das "X" geklickt wird, wird ein XbeP_Close an das XbpDialog() Element gesendet. Diese Nachricht leitest Du weiter und schliesst damit das XbpDialog() Element.

Drückst Du ESC, wird ein anderes Event generiert, und auch ein anderes Element als oXbp zurückgegeben. Dein :destroy() richtet sich nicht zwingend an das XbpDialog(). Ich würde im Debugger mal schauen, welches Element bei dem Keyboard Event geliefert wird.


Gruss,

Georg

P.S.: Am besten direkt komplett auf GUI umstellen. Das tut dann ein paar Wochen weh, aber danach ist man froh, dass der Schrecken (XbpCRT) ein Ende hat.

Re: xbpcrt und GUI

Verfasst: Mo, 03. Sep 2012 4:57
von AUGE_OHR
saul hat geschrieben:Leider ist eine kopmplette Umstellung aus Zeitgründen nicht zu machen.
wie viele Zeilen hat dein Code ?
schon mal über 3-PP Zusatz Software wie Express++, Topdown, DsClass & Co nachgedacht ?
saul hat geschrieben:

Code: Alles auswählen

  oXbp:destroy()
?"Hier bin ich wieder im CRT Fenster"
wait
RETURN
Gehe ich mit der ESC Taste raus, so erscheint auf dem CRT Fenster '"Weiter mit einer Taste, aber das Dialogfenster ohne den Browseteil bleibt stehen und das Programm läßt sich nur über ALT+C verlassen.
Schließe ich das GUI FEnster über das X rechts oben in der Titelzeile, so wird das GUI Fenster vollständig beseitigt und ich kann mittels einer Taste im Programm fortfahren.
Was mache ich beim Aussteig mittels ESC Taste falsch?
es gibt 2 Function

Code: Alles auswählen

SetAppFocus()
SetAppWindow()
eine "Eingabe" kannst du nur in dem "Fenster" ( SetAppWindow() ) machen welches den "Focus" ( SetAppFocus() ) hat.
bei Xbase++ "Hybrid" ist das "Problem" das die "Ausgabe" aber "keine Ahnung" hat ob sie nun gerade den "Focus" hat.

wenn du von einem "Hybrid Fenster" in ein GUI "Fenster" gehst musst du dafür sorgen das das "Hybrid Fenster" keine "Ausgabe" während der Zeit macht. wenn du nun dein GUI "Fenster" verlässt und "zerstörst" ( o:Destroy() ) dann bekommt dein "Hybrid Fenster" nicht "automatisch" den "Focus" ... es ist ein "Fenster" -> SetAppWindow(oCrt)

wenn du jetzt fragt "wo" kommt das oCrt her

Code: Alles auswählen

PROCEDURE MAIN
LOCAL oCrt := SetAppWindow()
// hier "normal" Cl*pper Code

oDialog := XbpDialog():New():Create()
// hier nun GUI

oDialog:destroy()
SetAppWindow(oCrt)
// hier wieder SAY / GET

Re: xbpcrt und GUI

Verfasst: Mo, 03. Sep 2012 5:51
von saul
Hallo,
danke für die Info. Alle Programme zusammen sind es ca. 35000 Zeilen Programmcode. Ist doch einiges in den Jahren zusammengekommen.

Wenn ich SetAppWindow(oCRT) vor oder nach destroy() setze bekomme ich eine Fehlermeldung das es die Variable oCRT nicht gibt. Stimmt, diese habe ich ja auch nicht definiert. Wie aber heißt das Objekt mit dem Fenster, welches zum Start des Programmes erstellt wird?

Ich weiß noch nicht warum, aber ich glaube ich habe eine Lösung gefunden.

Code: Alles auswählen

SetAppFocus( oBrowse )
SetAppWindow(oXbp)                                            // habe ich jetzt neu hinzugefügt
nEvent = 0
DO WHILE nEvent <> xbeP_Close
  nEvent := AppEvent( @mp1, @mp2, @oXbp )
  DO CASE
    CASE nEvent == xbeP_Keyboard .AND. mp1 == xbeK_ESC
      PostAppEvent( xbeP_Close )                            // habe ich jetzt neu hinzugefügt
    OTHERWISE
      oXbp:handleEvent( nEvent, mp1, mp2 )
  ENDCASE
ENDDO
oXbp:destroy()
Ehrlich gesagt, trotz Lesen der Hilfe ist mir der Unterschied zwischen setappfocus und setappwindows noch nicht ganz klar. Ist "focus" immer browse und "windows" immer dialog?

Wolfgang

Re: xbpcrt und GUI

Verfasst: Mo, 03. Sep 2012 6:25
von AUGE_OHR
saul hat geschrieben:Alle Programme zusammen sind es ca. 35000 Zeilen Programmcode. Ist doch einiges in den Jahren zusammengekommen.
Zeit zum "aufräumen" ;)
wenn du auf "full" GUI Umstellen willst fallen schon mal alle "Masken" weg.
btw. : schon mal den Xbase++ Formdesigner XppFD.EXE ausprobiert ?
saul hat geschrieben:Ehrlich gesagt, trotz Lesen der Hilfe ist mir der Unterschied zwischen setappfocus und setappwindows noch nicht ganz klar. Ist "focus" immer browse und "windows" immer dialog?
SetAppWindow() benötigst du eigentlich nur für das "Hybrid Fenster".
der "Main" Dialog ist ja nun unter Windows MDI der Parent für die Child Fenster und dafür brauchst du SetAppFocus() um ein bestimmtest XbPart anzusprechen.

da du nun den schwerem Weg, ohne 3-PP Libs, gehen willst eine persönliche Empfehlung : fange mit einem XbpDialog an und lasse deine Cl*pper Code in einem CRT "Fenster" auf der o:DrawingArea laufen.

Code: Alles auswählen

PROCEDURE APPSYS
RETURN

PROCEDURE MAIN
LOCAL oMainDialog 
LOCAL oCRT

   oMainDialog := XbpDialog():New(AppDesktop,,aPos,aSize)
   ...
   oMainDialog:Create()
   CreateMenuSystem( oMainDialog)

   DO WHILE nEvent <> xbeP_Close
      nEvent := AppEvent( @mp1, @mp2, @oXbp )
      oXbp:handleEvent( nEvent, mp1, mp2 )
   ENDDO
   oMainDialog:Destroy()
RETURN

PROCEDURE CreateMenuSystem( oMainDialog)
LOCAL oMenu
LOCAL oMenuBar := oMainDialog:menuBar()

   oMenu       := XbpMenu():new( oMenuBar )
   oMenu:title := "~Programm"
   oMenu:create()
   oMenu:addItem( { "~Programm"   , {|| MyCRT(oMainDialog) }})
   oMenubar:addItem( { oMenu, NIL} )

   oMenu       := XbpMenu():new( oMenuBar )
   oMenu:title := "~Ende"
   oMenu:create()
   oMenu:addItem( { "~Ende"         , {|| APPQUIT() } } )
   oMenubar:addItem( { oMenu, NIL} )

RETURN oMenubar


PROCEDURE MyCRT(oMainDialog)

   oCRT := XbpCRT():New(oMainDialog:DrawingArea,, aCrtPos, nRow, nCol )
   ...
   oCRT:Create()
   SetAppWindow(oCRT)
   // hier Cl*pper Code


   // bevor es zurück geht
   SetAppWindow(oMainDialog)
RETURN