Unlimited events (Canvas inside ScrollArea)
Posted: Wed Mar 04, 2026 11:09 am
Hi,
Add boxes to create a scroll
Hover your mouse over any box
Events fire when the mouse moves
Now scroll down to the very bottom
Hover your mouse over any box
Events don't stop
PureScrollArea and PureCanvas are custom window classes
And maybe bug inside it
Tested on Win10x64 PB630x64
Add boxes to create a scroll
Hover your mouse over any box
Events fire when the mouse moves
Now scroll down to the very bottom
Hover your mouse over any box
Events don't stop
PureScrollArea and PureCanvas are custom window classes
And maybe bug inside it
Tested on Win10x64 PB630x64
Code: Select all
EnableExplicit
#window = 0
#window_width = 300
#window_height = 400
#window_margin = 5
#button_width = 80
#button_height = 25
#boxes_width = 200
#boxes_height = 50
#boxes_borders = 4
Enumeration; gadgets
#button
#scrollarea
#canvas
EndEnumeration
Structure boxes_list
color.l
y.i
h.i
selected.b
EndStructure
NewList boxes.boxes_list()
Define window_handle
Define vscroll_size, hscroll_size
Declare redraw_boxes()
;- procedures
Procedure resize_window()
Shared window_handle
Protected window_width, window_height
window_width = WindowWidth(#window)
window_height = WindowHeight(#window)
ResizeGadget(#scrollarea, window_width - #boxes_width - #window_margin, #window_margin, #boxes_width, window_height - #window_margin * 2)
redraw_boxes()
EndProcedure
Procedure.b open_window()
Shared window_handle
Protected result.b
window_handle = OpenWindow(#window, #PB_Ignore, #PB_Ignore, #window_width, #window_height, "unlimited events", #PB_Window_SystemMenu | #PB_Window_ScreenCentered | #PB_Window_SizeGadget | #PB_Window_MinimizeGadget | #PB_Window_MaximizeGadget)
If window_handle
ButtonGadget(#button, 5, 5, #button_width, #button_height, "Add box")
ScrollAreaGadget(#scrollarea, 0, 0, 0, 0, 0, 0, #PB_ScrollArea_BorderLess)
CanvasGadget(#canvas, 0, 0, 0, 0)
CloseGadgetList()
WindowBounds(#window, #window_width, #window_height, #PB_Ignore, #PB_Ignore)
SmartWindowRefresh(#window, #True)
BindEvent(#PB_Event_SizeWindow, @resize_window(), #window)
result = #True
EndIf
ProcedureReturn result
EndProcedure
Procedure redraw_boxes()
Shared boxes()
Shared vscroll_size
Protected boxes_height
Protected vscroll_enabled.b
If GadgetHeight(#scrollarea) > 0
ForEach boxes()
boxes_height + #boxes_height
Next
If boxes_height > GadgetHeight(#scrollarea) - #boxes_borders
vscroll_enabled = #True
SetGadgetAttribute(#scrollarea, #PB_ScrollArea_InnerWidth, #boxes_width - DesktopUnscaledX(#boxes_borders) - DesktopUnscaledX(vscroll_size))
SetGadgetAttribute(#scrollarea, #PB_ScrollArea_InnerHeight, boxes_height)
ResizeGadget(#canvas, 0, 0, #boxes_width - DesktopUnscaledX(#boxes_borders) - DesktopUnscaledX(vscroll_size), boxes_height)
Debug "REDRAW with SCROLL " + Str(ElapsedMilliseconds())
Else
SetGadgetAttribute(#scrollarea, #PB_ScrollArea_InnerWidth, #boxes_width - DesktopUnscaledX(#boxes_borders))
SetGadgetAttribute(#scrollarea, #PB_ScrollArea_InnerHeight, boxes_height)
ResizeGadget(#canvas, 0, 0, #boxes_width - DesktopUnscaledX(#boxes_borders), boxes_height)
Debug "REDRAW " + Str(ElapsedMilliseconds())
EndIf
If StartDrawing(CanvasOutput(#canvas))
boxes_height = 0
ForEach boxes()
boxes()\y = DesktopScaledY(boxes_height)
boxes_height + #boxes_height
boxes()\h = DesktopScaledY(boxes_height) - boxes()\y
Next
ForEach boxes()
If boxes()\selected = #True
Box(0, boxes()\y, DesktopScaledX(GadgetWidth(#canvas)), boxes()\h, RGB(Red(boxes()\color) * 0.5, Green(boxes()\color) * 0.5, Blue(boxes()\color) * 0.5))
Else
Box(0, boxes()\y, DesktopScaledX(GadgetWidth(#canvas)), boxes()\h, boxes()\color)
EndIf
Next
StopDrawing()
EndIf
EndIf
EndProcedure
Procedure add_box()
Shared boxes()
AddElement(boxes())
boxes()\color = RGB(Random(255, 100), Random(255, 100), Random(255, 100))
redraw_boxes()
EndProcedure
Procedure canvas_boxes(event_type)
Shared boxes()
Protected mouse_x, mouse_y
Select event_type
Case #PB_EventType_MouseLeave
ForEach boxes()
boxes()\selected = #False
Next
redraw_boxes()
Case #PB_EventType_MouseMove
mouse_x = GetGadgetAttribute(#canvas, #PB_Canvas_MouseX)
mouse_y = GetGadgetAttribute(#canvas, #PB_Canvas_MouseY)
ForEach boxes()
If mouse_y >= boxes()\y And mouse_y <= boxes()\y + boxes()\h - 1
boxes()\selected = #True
Else
boxes()\selected = #False
EndIf
Next
redraw_boxes()
EndSelect
EndProcedure
Procedure main_loop()
Shared window_handle
Shared boxes()
Repeat
Select WaitWindowEvent()
Case #PB_Event_Gadget
Select EventGadget()
Case #button: add_box()
Case #canvas: canvas_boxes(EventType())
EndSelect
Case #PB_Event_CloseWindow
Break
EndSelect
ForEver
If window_handle
CloseWindow(#window)
EndIf
EndProcedure
;- main code
vscroll_size = GetSystemMetrics_(#SM_CXVSCROLL)
If open_window()
resize_window()
main_loop()
EndIf
End