How to stop ListIconGadget from flickering on resize?

Just starting out? Need help? Post your questions and find answers here.
PB
PureBasic Expert
PureBasic Expert
Posts: 7581
Joined: Fri Apr 25, 2003 5:24 pm

Post by PB »

> Resize the window so that it's large

Ah, now I see it. :)

I fixed it on my PC by changing #WM_SIZE to #WM_SIZING in the callback.
Makes the large window show almost no flicker when resizing right to left.
But as the saying goes: YMMV. :)
PB
PureBasic Expert
PureBasic Expert
Posts: 7581
Joined: Fri Apr 25, 2003 5:24 pm

Post by PB »

So, Mistrel, did you try changing the flag like I mentioned above?
Mistrel
Addict
Addict
Posts: 3415
Joined: Sat Jun 30, 2007 8:04 pm

Post by Mistrel »

By changing #WM_SIZE to #WM_SIZING for the window callback the gadgets no longer resize to the width of the window when the splitter is moved.

Using 'Case #WM_SIZE, #WM_SIZING' does not reduce the flickering.
PB
PureBasic Expert
PureBasic Expert
Posts: 7581
Joined: Fri Apr 25, 2003 5:24 pm

Post by PB »

> the gadgets no longer resize to the width of the window when the splitter is moved

They do here. Using either flag makes the gadgets act the same, except by using
#WM_SIZING I don't get any flicker.
Mistrel
Addict
Addict
Posts: 3415
Joined: Sat Jun 30, 2007 8:04 pm

Post by Mistrel »

Would you post your callback?
Mistrel
Addict
Addict
Posts: 3415
Joined: Sat Jun 30, 2007 8:04 pm

Post by Mistrel »

Fixed. :)

Also to one-up srod. ( http://www.purebasic.fr/english/viewtopic.php?t=35334 ) :twisted:

Code: Select all

Enumeration
	#Main
	#Main_Web
	#Main_Combo
	#Main_List
	#Main_Container
	#Main_Splitter
	#Main_Panel
EndEnumeration

Global OldSplitterCallback
Global OldPanelCallback
Procedure WinCallback(hWnd, uMsg, wParam, lParam)
	Select uMsg
		Case #WM_WINDOWPOSCHANGED
			ResizeGadget(#Main_Splitter,#PB_Ignore,#PB_Ignore,WindowWidth(#Main)-10,WindowHeight(#Main)-10)
			ResizeGadget(#Main_Combo,#PB_Ignore,#PB_Ignore,GadgetWidth(#Main_Container),#PB_Ignore)
			ResizeGadget(#Main_List,#PB_Ignore,#PB_Ignore,GadgetWidth(#Main_Container),GadgetHeight(#Main_Container)-25)
	EndSelect
	ProcedureReturn #PB_ProcessPureBasicEvents
EndProcedure

Procedure SplitterCallback(hWnd, uMsg, wParam, lParam)
	Result=CallWindowProc_(OldSplitterCallback, hWnd, uMsg, wParam, lParam)
	Select uMsg
		Case #WM_ERASEBKGND
			Result=1
		Case #WM_WINDOWPOSCHANGED
			RedrawWindow_(hWnd,0,0,#RDW_UPDATENOW)
		Case #WM_MOUSEMOVE
			RedrawWindow_(hWnd,0,0,#RDW_UPDATENOW)
	EndSelect
	ProcedureReturn Result
EndProcedure

Procedure PanelCallback(hWnd, uMsg, wParam, lParam)
	Result=CallWindowProc_(OldPanelCallback, hWnd, uMsg, wParam, lParam)
	Select uMsg
		Case #WM_WINDOWPOSCHANGED
			RedrawWindow_(hWnd,0,0,#RDW_UPDATENOW)
	EndSelect
	ProcedureReturn Result
EndProcedure

If OpenWindow(#Main,#False,#False,420,235,"Test",#PB_Window_SystemMenu|#PB_Window_ScreenCentered|#PB_Window_SizeGadget)
;	 WebGadget(#Main_Web,0,0,0,0,"")
	PanelGadget(#Main_Panel,0,0,0,0)
	AddGadgetItem(#Main_Panel,-1,"Sub-Panel 1")
	AddGadgetItem(#Main_Panel,-1,"Sub-Panel 2")
	AddGadgetItem(#Main_Panel,-1,"Sub-Panel 3")

	CloseGadgetList()
	ContainerGadget(#Main_Container,0,0,0,0)
	ComboBoxGadget(#Main_Combo,0,0,160,200)
	ListIconGadget(#Main_List,0,25,160,200,"Test",70,#PB_ListIcon_FullRowSelect|#PB_ListIcon_HeaderDragDrop)
	AddGadgetColumn(#Main_List,1,"Test2",160)
	AddGadgetColumn(#Main_List,2,"Test3",60)
	For i=0 To 100
		AddGadgetItem(#Main_List,-1,"HelloHello"+#LF$+"HelloHelloHelloHello"+#LF$+"Hello")
	Next
	CloseGadgetList()
	SplitterGadget(#Main_Splitter,5,5,410,225,#Main_Panel,#Main_Container,#PB_Splitter_Vertical)
EndIf

ResizeGadget(#Main_Splitter,#PB_Ignore,#PB_Ignore,WindowWidth(#Main)-10,WindowHeight(#Main)-10)
ResizeGadget(#Main_Combo,#PB_Ignore,#PB_Ignore,GadgetWidth(#Main_Container),#PB_Ignore)
ResizeGadget(#Main_List,#PB_Ignore,#PB_Ignore,GadgetWidth(#Main_Container),GadgetHeight(#Main_Container)-25)
	
hWnd=GadgetID(#Main_Container)
SetWindowLongPtr_(hWnd,#GWL_STYLE,GetWindowLong_(hWnd,#GWL_STYLE)|#WS_CLIPCHILDREN)
OldSplitterCallback=SetWindowLongPtr_(GadgetID(#Main_Splitter),#GWL_WNDPROC,@SplitterCallback())
OldPanelCallback=SetWindowLongPtr_(GadgetID(#Main_Panel),#GWL_WNDPROC,@PanelCallback())
SetWindowLongPtr_(GadgetID(#Main_Panel),#GWL_EXSTYLE,GetWindowLong_(GadgetID(#Main_Panel),#GWL_EXSTYLE)|#WS_EX_COMPOSITED&(~#WS_EX_TRANSPARENT))
SetParent_(FindWindowEx_(GadgetID(#Main_Panel),0,"msctls_updown32",0),GadgetID(#Main_Splitter))

SetWindowCallback(@WinCallback(),#Main)

Repeat
Until WaitWindowEvent()=#WM_CLOSE
Last edited by Mistrel on Sat Feb 21, 2009 10:25 am, edited 2 times in total.
Sparkie
PureBatMan Forever
PureBatMan Forever
Posts: 2307
Joined: Tue Feb 10, 2004 3:07 am
Location: Ohio, USA

Post by Sparkie »

#WS_EX_COMPOSITED = 95% to 99% CPU usage when idle. If you must use #WS_EX_COMPOSITED I would suggest toggling it off/on as needed. :roll: :wink:
What goes around comes around.

PB 5.21 LTS (x86) - Windows 8.1
Mistrel
Addict
Addict
Posts: 3415
Joined: Sat Jun 30, 2007 8:04 pm

Post by Mistrel »

It's not #WS_EX_COMPOSITED per se. This style is extremely finicky and won't work at all with some gadgets (like the list view) and it doesn't always play well with some child windows. In this case we need to move the panel's left/right arrows to a different parent within the same container. This way you still get double-buffering but without the child's message queue being flooded. :)

I've updated the example for you.

There may be a better solution by double-buffering by hand. This style is a very poor implementation.
Mistrel
Addict
Addict
Posts: 3415
Joined: Sat Jun 30, 2007 8:04 pm

Post by Mistrel »

Fixed a bug where I was acquiring a style from the wrong gadget. Also, the tab gadget will be mostly flicker-free if you disable #WS_EX_TRANSPARENT. #WS_EX_COMPOSITED eliminates all flickering but must be used in conjunction with disabling #WS_EX_TRANSPARENT on the panel gadget.

Sorry to bump this but it is a very useful thread on how to handle flickering.
srod
PureBasic Expert
PureBasic Expert
Posts: 10589
Joined: Wed Oct 29, 2003 4:35 pm
Location: Beyond the pale...

Post by srod »

Have you tried adding a button gadget to the panel whilst using the #WS_EX_COMPOSITED style? Doesn't work here on either Vista or XP; although they exhibit different problems.
I may look like a mule, but I'm not a complete ass.
PrincieD
Addict
Addict
Posts: 858
Joined: Wed Aug 10, 2005 2:08 pm
Location: Yorkshire, England
Contact:

Post by PrincieD »

This should solve your problem :)

Code: Select all

SendMessage_(GadgetID(#ListIcon), #LVM_SETEXTENDEDLISTVIEWSTYLE , #LVS_EX_DOUBLEBUFFER , #LVS_EX_DOUBLEBUFFER)
gnozal
PureBasic Expert
PureBasic Expert
Posts: 4229
Joined: Sat Apr 26, 2003 8:27 am
Location: Strasbourg / France
Contact:

Post by gnozal »

PrincieD wrote:This should solve your problem :)

Code: Select all

SendMessage_(GadgetID(#ListIcon), #LVM_SETEXTENDEDLISTVIEWSTYLE , #LVS_EX_DOUBLEBUFFER , #LVS_EX_DOUBLEBUFFER)
Iirc Microsoft Windows XP or later only and themes activated.
For free libraries and tools, visit my web site (also home of jaPBe V3 and PureFORM).
srod
PureBasic Expert
PureBasic Expert
Posts: 10589
Joined: Wed Oct 29, 2003 4:35 pm
Location: Beyond the pale...

Post by srod »

PrincieD wrote:This should solve your problem :)

Code: Select all

SendMessage_(GadgetID(#ListIcon), #LVM_SETEXTENDEDLISTVIEWSTYLE , #LVS_EX_DOUBLEBUFFER , #LVS_EX_DOUBLEBUFFER)
We're talking about the panel gadget not the ListIcon!!! I tried it anyhow and it made no difference.

What I am saying is that if you add a button gadget to the panel gadget then the button is simply not rendered correctly here on Vista or XP because of the #WS_EX_COMPOSITED extended style.
I may look like a mule, but I'm not a complete ass.
PrincieD
Addict
Addict
Posts: 858
Joined: Wed Aug 10, 2005 2:08 pm
Location: Yorkshire, England
Contact:

Post by PrincieD »

We're talking about the panel gadget not the ListIcon!!! I tried it anyhow and it made no difference.

What I am saying is that if you add a button gadget to the panel gadget then the button is simply not rendered correctly here on Vista or XP because of the #WS_EX_COMPOSITED extended style.
Ahh my bad, sorry :) the double buffering flag does work with the listicon though (and yes it's contained in a spliter, answering the original question), I have no flickering whatsoever in DCC Manager (you still need the clipchildren on the main window though)

PB's panel gadgets are a bit dodge I'm afraid, thats why I wrote my own panel control in ProGUI. For instance, static controls need special consideration as they are rendered with a background brush.

Anyway, just thought I'd give my 2 cents as I've had quite a bit of experience getting rid of flickering.
srod
PureBasic Expert
PureBasic Expert
Posts: 10589
Joined: Wed Oct 29, 2003 4:35 pm
Location: Beyond the pale...

Post by srod »

I was just investigating the #WS_EX_COMPOSITED extended style and, well, I have to say that it isn't up to much if my tests are anything to go by!!!
I may look like a mule, but I'm not a complete ass.
Post Reply