Events während des Verschiebens eines Fensters

Anfängerfragen zum Programmieren mit PureBasic.
Benutzeravatar
Kurzer
Beiträge: 1617
Registriert: 25.04.2006 17:29
Wohnort: Nähe Hamburg

Beitrag von Kurzer »

Würde gern wissen, ob es richtig ist, daß ich mich bei der Bearbeitung der #WM_PAINT Message innerhalb eines Callbacks auch um die Restaurierung des Festerhintergrunds kümmern muß.

Erst zeichnete ich im #WM_PAINT nur die beiden Bilder in dem Preview-Window neu.
Das hatte aber zur Folge, daß die Zwischenräume während des Verschiebens des Fensters nicht refresched wurden (erst, wenn ich später mit nem anderen Window drüberging). Dabei kam dann u.U. sowas raus, wie in dem vorletzten Screenshot.
Nu geh ich her und zeichen auch die Zwischenräume selbst neu (im letzten Screenshoot durch farbige BOXen angedeutet).
F1: Ist das so gewollt von Windows?

Dann fiel mir auf, daß die Ermittlung der Hintergrundfarbe des Fensters mit GetSysColor_(#COLOR_WINDOW) die Farbe weiß zurückliefert, obwohl der Fensterhintergrund grau ist.
F2: Liegt das evtl. an PureBasic, daß es das Fenster mit einer anderen Hintergrundfarbe geöffnet hat?

Die Situation hier ist die, daß ich mir einige Dinge aus C-sourcecodes abgucke und sie in PB verwenden möchte. Evtl. liegt das Problem ja auch daran. In C wird ein Fenster ja ganz anders geöffnet als in PB. Ich weiß nicht ob PBs OpenWindow() den gleichen Code erzeugt, wie ein C Äquivalent.
"Never run a changing system!" | "Unterhalten sich zwei Alleinunterhalter... Paradox, oder?"
PB 6.12 x64, OS: Win 11 24H2 x64, Desktopscaling: 150%, CPU: I7 12700 H, RAM: 32 GB, GPU: Intel(R) Iris(R) Xe Graphics | NVIDIA GeForce RTX 3070
Useralter in 2025: 57 Jahre.
Benutzeravatar
Fluid Byte
Beiträge: 3110
Registriert: 27.09.2006 22:06
Wohnort: Berlin, Mitte

Beitrag von Fluid Byte »

F1: Ist das so gewollt von Windows?
Ja, du bist verantwortlich für den gesamten Fensterinhalt. Du kannst aber das Aktualisieren der Zwischenräume umgehen in dem eine geclippte DC benutzt, sprich ein Fenster mit passender Größe wie z. B. ein ImageGadget().
F2: Liegt das evtl. an PureBasic, daß es das Fenster mit einer anderen Hintergrundfarbe geöffnet hat?
Nein, das ist korrekt so. Mit #COLOR_WINDOW bekommst du den Wert für den Hintergrund von Fenstern bzw. dessen Controls. Wenn du einen Ordner öffnest ist die Hintergrund Farbe (soweit nicht in "Anzeige" geändert) standardmäßig auch weiß. Die Farbe die du suchst bekommst du mit #COLOR_3DFACE.
Windows 10 Pro, 64-Bit / Outtakes | Derek
Benutzeravatar
NicTheQuick
Ein Admin
Beiträge: 8809
Registriert: 29.08.2004 20:20
Computerausstattung: Ryzen 7 5800X, 64 GB DDR4-3200
Ubuntu 24.04.2 LTS
GeForce RTX 3080 Ti
Wohnort: Saarbrücken

Beitrag von NicTheQuick »

Du kannst doch auch 'InvalidateRect_()' einen rechteckigen Bereich
übergeben, der refresht werden soll. Dann übergibst du da eben alle
Bereiche, die zwischen deinen Bildern liegen. Also die, die da zum Test farbig
gemacht hast.
Benutzeravatar
scholly
Beiträge: 793
Registriert: 04.11.2005 21:30
Wohnort: Düsseldorf

Beitrag von scholly »

Fluid Byte hat geschrieben: Die Farbe die du suchst bekommst du mit #COLOR_3DFACE.
Habe ich das jetzt richtig verstanden:

Code: Alles auswählen

win_bg = GetSysColor_(#COLOR_3DFACE)
ist (unter Windows) ein schnellerer, vollständiger Ersatz für

Code: Alles auswählen

 StartDrawing(WindowOutput(0))
   win_bg = Point(1,1)
 StopDrawing()
Und auch sicherer, weil ein verdecktes (1,1) keine Fehlinfo ermittelt?

:allright: Mr. Api :lol:
Ich bin blutiger PB-Anfänger.
seit 17.12.08: PB 4.3 unter XP Home(SP3)
Benutzeravatar
Fluid Byte
Beiträge: 3110
Registriert: 27.09.2006 22:06
Wohnort: Berlin, Mitte

Beitrag von Fluid Byte »

NicTheQuick hat geschrieben:Du kannst doch auch 'InvalidateRect_()' einen rechteckigen Bereich
übergeben, der refresht werden soll. Dann übergibst du da eben alle
Bereiche, die zwischen deinen Bildern liegen. Also die, die da zum Test farbig
gemacht hast.
Natürlich gibt es diverse Möglichkeiten nur bestimmte Breiche zu refreshen ist aber unüblich bzw. umständlich hier. Es einfacher und eleganter eine eigene geclippte DC mittels eines seperaten Fensters zu erstellen. Warum gibts wohl ein ImageGadget()? Bild
Windows 10 Pro, 64-Bit / Outtakes | Derek
Benutzeravatar
Kurzer
Beiträge: 1617
Registriert: 25.04.2006 17:29
Wohnort: Nähe Hamburg

Beitrag von Kurzer »

Ich hatte erst zwei Imagegadgets für die beiden Bilder, aber dann gab es (für mich) Probleme, weil die das Image nicht skalieren können. Daher bin ich auf DrawImage direkt ins Fenster umgestiegen.
http://www.purebasic.fr/german/viewtopi ... 759#191759

Aber mittlerweile bin ich im Bereich API zu StretchBlt() vorgedrungen und ich sehe, man könnte in der Tat wieder zwei Imagegadgets als Art Container nutzen um dort die Images mittles API (StretchBlt) innerhalb der #WM_Paint reinwuppen. Ich denke, daß Du das meinst.
Und es ist sicher, den Rest des Windows refreshed Windows selbst (auch während des verschiebens)?
"Never run a changing system!" | "Unterhalten sich zwei Alleinunterhalter... Paradox, oder?"
PB 6.12 x64, OS: Win 11 24H2 x64, Desktopscaling: 150%, CPU: I7 12700 H, RAM: 32 GB, GPU: Intel(R) Iris(R) Xe Graphics | NVIDIA GeForce RTX 3070
Useralter in 2025: 57 Jahre.
Benutzeravatar
edel
Beiträge: 3667
Registriert: 28.07.2005 12:39
Computerausstattung: GameBoy
Kontaktdaten:

Beitrag von edel »

Versuch mal folgende Variante :

Code: Alles auswählen

Global oldProc

Procedure c(h,m,w,p)
   
   result = CallWindowProc_(oldProc,h,m,w,p)
   
   If m = #WM_PAINT   	
      StartDrawing(WindowOutput(0))
         Box(0,0,300,300,$5F8EA0)
      StopDrawing() 
      ProcedureReturn result    
   EndIf
   
   ProcedureReturn result
EndProcedure


h = OpenWindow(0,0,0,300,300,"")
oldProc = SetWindowLong_(h,#GWL_WNDPROC,@c())

Repeat
   e = WaitWindowEvent()
Until e = 16
Benutzeravatar
Kurzer
Beiträge: 1617
Registriert: 25.04.2006 17:29
Wohnort: Nähe Hamburg

Beitrag von Kurzer »

Danke für die Mühe, Edel, leider bringt das auch keien Abhilfe. Aber ich merke gerade, daß das Problem eh hausgemacht ist.

Das Fenster ist erst groß mit großen Images darin und wird dann einfach nur auf die Hälfte verkleinert. Logisch, daß da die Reste von den großen Images an den Rändern kleben, wenn ich die vor dem Verkleinern des Fensters nicht lösche. Sorry für den Aufstand... :oops:
Nu lösche ich das Fenster kompett mit der (richtigen) Hintergrundfarbe (Danke Fluid Byte), resize dann und zeichne die Images neu.
Das flackert zwar einmal beim resizen kurz, aber das ist zu verschmerzen.
WM_PAINT im Callback war irgendwie die falsche Stelle, an der ich rumgedoktort habe.
"Never run a changing system!" | "Unterhalten sich zwei Alleinunterhalter... Paradox, oder?"
PB 6.12 x64, OS: Win 11 24H2 x64, Desktopscaling: 150%, CPU: I7 12700 H, RAM: 32 GB, GPU: Intel(R) Iris(R) Xe Graphics | NVIDIA GeForce RTX 3070
Useralter in 2025: 57 Jahre.
Benutzeravatar
Fluid Byte
Beiträge: 3110
Registriert: 27.09.2006 22:06
Wohnort: Berlin, Mitte

Beitrag von Fluid Byte »

Alles schicki lacki jetzt oder wat?
Windows 10 Pro, 64-Bit / Outtakes | Derek
Benutzeravatar
Kurzer
Beiträge: 1617
Registriert: 25.04.2006 17:29
Wohnort: Nähe Hamburg

Beitrag von Kurzer »

Jupp, da ich durch den CallBack ja selbst für das gesamte Fenster verantwortlich bin, sollte die jetzige Lösung richtig sein. :allright:
"Never run a changing system!" | "Unterhalten sich zwei Alleinunterhalter... Paradox, oder?"
PB 6.12 x64, OS: Win 11 24H2 x64, Desktopscaling: 150%, CPU: I7 12700 H, RAM: 32 GB, GPU: Intel(R) Iris(R) Xe Graphics | NVIDIA GeForce RTX 3070
Useralter in 2025: 57 Jahre.
Antworten