Page 1 of 1
How to check if EventData() is defined?
Posted: Wed Sep 04, 2024 6:22 am
by TI-994A
The
PostEvent() function is able to include some data with its custom event:
PureBasic Manual wrote:EventData()
Return value: If the current event isn't a custom event sent with PostEvent(), this value is undefined.
Is there a way to determine if
EventData() has been defined?
Re: How to check if EventData() is defined?
Posted: Wed Sep 04, 2024 6:51 am
by infratec
For what you need this?
If you have a custom event , you have your own 'endpoint' in the eventloop, then you can ask for this value.
If it is a 'normal' PB event, you should not use eventdata. Maybe it is already used by the PB events.
Re: How to check if EventData() is defined?
Posted: Wed Sep 04, 2024 7:05 am
by TI-994A
infratec wrote: Wed Sep 04, 2024 6:51 amIf it is a 'normal' PB event, you should not use eventdata. Maybe it is already used by the PB events.
Hi Bernd. Yes, maybe. Although I don't suppose so.
The documentation expressly mentions the use of the
PostEvent() function with PureBasic events as well;
with no caveats.
The data would be useful to differentiate between system-initiated events and user-posted ones.
Re: How to check if EventData() is defined?
Posted: Wed Sep 04, 2024 9:01 am
by mk-soft
Normally you use your own custom events.
For standard events, eventdata is null
Code: Select all
;-TOP
#ProgramTitle = "Main Window"
#Version = "v1.01.1"
Enumeration Windows
#Main
EndEnumeration
Enumeration Menus
#MainMenu
EndEnumeration
Enumeration MenuItems
#MainMenuExitApplication
EndEnumeration
Enumeration Gadgets
EndEnumeration
Enumeration Status
#MainStatusBar
EndEnumeration
Global ExitApplication
; ----
; ---- String Helper ----
Procedure AllocateString(String.s) ; Result = Pointer
Protected *mem.string = AllocateStructure(String)
If *mem
*mem\s = String
EndIf
ProcedureReturn *mem
EndProcedure
Procedure.s FreeString(*mem.string) ; Result String
Protected r1.s
If *mem
r1 = *mem\s
FreeStructure(*mem)
EndIf
ProcedureReturn r1
EndProcedure
; ----
Procedure DoEventCloseWindow()
Protected window = EventWindow()
Protected *pdata = EventData()
Protected text.s
If *pdata = 0
Debug "Do any before event close window ..."
PostEvent(#PB_Event_CloseWindow, window, 0, 0, AllocateString("Do Close Window Event 2"))
Else
text = FreeString(*pdata)
Debug text
ExitApplication = #True
EndIf
EndProcedure
Procedure UpdateWindow()
Protected dx, dy
dx = WindowWidth(#Main)
dy = WindowHeight(#Main) - StatusBarHeight(#MainStatusBar) - MenuHeight()
; Resize gadgets
EndProcedure
; ----
Procedure Main()
Protected dx, dy
#MainStyle = #PB_Window_SystemMenu | #PB_Window_SizeGadget | #PB_Window_MaximizeGadget | #PB_Window_MinimizeGadget
If OpenWindow(#Main, #PB_Ignore, #PB_Ignore, 800, 600, #ProgramTitle , #MainStyle)
; Menu
CreateMenu(#MainMenu, WindowID(#Main))
MenuTitle("File")
MenuItem(#MainMenuExitApplication, "E&xit")
; For Mac
CompilerIf #PB_Compiler_OS = #PB_OS_MacOS
If Not IsMenu(#MainMenu)
CreateMenu(#MainMenu, WindowID(#Main))
EndIf
MenuItem(#PB_Menu_About, "")
MenuItem(#PB_Menu_Preferences, "")
CompilerEndIf
; StatusBar
CreateStatusBar(#MainStatusBar, WindowID(#Main))
AddStatusBarField(#PB_Ignore)
StatusBarText(#MainStatusBar, 0, " " + #Version)
; Gadgets
dx = WindowWidth(#Main)
dy = WindowHeight(#Main) - StatusBarHeight(#MainStatusBar) - MenuHeight()
; Bind events
BindEvent(#PB_Event_SizeWindow, @UpdateWindow(), #Main)
BindEvent(#PB_Event_CloseWindow, @DoEventCloseWindow(), #Main, 0)
; Main loop
Repeat
Select WaitWindowEvent()
Case #PB_Event_CloseWindow
;ExitApplication = #True
Case #PB_Event_Menu
Select EventMenu()
CompilerIf #PB_Compiler_OS = #PB_OS_MacOS
Case #PB_Menu_About
MessageRequester("Info", #ProgramTitle + " " + #Version)
Case #PB_Menu_Preferences
Case #PB_Menu_Quit
;ExitApplication = #True
PostEvent(#PB_Event_CloseWindow, #Main, 0))
CompilerEndIf
Case #MainMenuExitApplication
;ExitApplication = #True
PostEvent(#PB_Event_CloseWindow, #Main, 0)
EndSelect
Case #PB_Event_Gadget
Select EventGadget()
EndSelect
EndSelect
Until ExitApplication
EndIf
EndProcedure : Main()
Re: How to check if EventData() is defined?
Posted: Wed Sep 04, 2024 10:25 am
by TI-994A
mk-soft wrote: Wed Sep 04, 2024 9:01 am
For standard events, eventdata is null...
Code: Select all
Procedure DoEventCloseWindow()
Protected window = EventWindow()
Protected *pdata = EventData()
Protected text.s
If *pdata = 0
Debug "Do any before event close window ..."
PostEvent(#PB_Event_CloseWindow, window, 0, 0, AllocateString("Do Close Window Event 2"))
Else
text = FreeString(*pdata)
Debug text
ExitApplication = #True
EndIf
EndProcedure
Hi @mk-soft, and thanks for the example. However, this is not always the case.
Code: Select all
; *********************************************
;
; EventData() not null with native events
;
; tested on Windows, macOS, and Linux
; with PureBasic x32 & x64 versions
;
; *********************************************
window = OpenWindow(#PB_Any, 100, 100, 600, 300,
"PureBasic PostEvent() Function",
#PB_Window_SystemMenu |
#PB_Window_ScreenCentered)
canvas = CanvasGadget(#PB_Any, 10, 10, 580, 240)
output = StringGadget(#PB_Any, 10, 260, 580, 30, "")
AddWindowTimer(window, 0, 5000)
MessageRequester("PostEvent() Example",
"Timer will simulate a left-click " +
"on the canvas gadget every 5 seconds. " +
"Manually left-click on the canvas gadget " +
"to see the value returned by EventData().")
Repeat
event = WaitWindowEvent()
Select event
Case #PB_Event_CloseWindow
appQuit = #True
Case #PB_Event_Timer
PostEvent(#PB_Event_Gadget, window, canvas, #PB_EventType_LeftClick,
@"Timer-initiated left-click on canvas gadget!")
Case #PB_Event_Gadget
If EventGadget() = canvas
*eData = EventData()
If EventType() = #PB_EventType_LeftClick
If *eData
eData.s = PeekS(*eData)
Else
eData.s = "User-initiated left-click on canvas gadget!"
EndIf
timeStamp.s = FormatDate("%hh:%ii:%ss", Date())
SetGadgetText(output, timeStamp + ": " + eData + " (EventData() = " + *eData +")")
EndIf
EndIf
EndSelect
Until appQuit
Re: How to check if EventData() is defined?
Posted: Wed Sep 04, 2024 12:22 pm
by Axolotl
Hi TI-994A,
I can only agree with the previous witers.
IMHO the correct value must be documented for pb events. Otherwise, I would not rely on (random values).
For my own events, I always use ZERO as undefined by definition. In exceptional cases also -1.
Re: How to check if EventData() is defined?
Posted: Wed Sep 04, 2024 12:40 pm
by spikey
TI-994A wrote: Wed Sep 04, 2024 10:25 am
However, this is not always the case.
But what you are doing in this case is turning a system event into a custom event by using #PB_EventType_LeftClick as an argument to PostEvent. By then specifying the data parameter too you're distorting both of these facilities slightly from their originally conceived purpose. There's always the possibility of unforeseen consequences in this sort of situation.
I'd be thinking about a fully custom event in this sort of circumstance.
It might be worth a feature request that standard events reset the EventData() value though...
Re: How to check if EventData() is defined?
Posted: Wed Sep 04, 2024 12:57 pm
by TI-994A
Axolotl wrote: Wed Sep 04, 2024 12:22 pm...I always use ZERO as undefined by definition. In exceptional cases also -1.
Sure; but
EventData() is not returning
0 or -1 for some of the native PureBasic events.
As demonstrated in my example.
Re: How to check if EventData() is defined?
Posted: Wed Sep 04, 2024 12:58 pm
by TI-994A
spikey wrote: Wed Sep 04, 2024 12:40 pm...turning a system event into a custom event by using #PB_EventType_LeftClick as an argument to PostEvent. By then specifying the data parameter too you're distorting both of these facilities slightly from their originally conceived purpose.
PureBasic Manual wrote:PostEvent()
Syntax: Result = PostEvent(Event [, Window, Object [, Type [, Data]]])
PureBasic allows the use of their own native events and event types in the
PostEvent() function. This would be most useful for simulating UI events.
Nevertheless, in my example, the PostEvent() function
(with the native event, event type, and custom data) is working well, without issue.
It is the system-triggered event that is causing the issue; where its EventData() is not null when it should be.
Re: How to check if EventData() is defined?
Posted: Wed Sep 04, 2024 4:42 pm
by Demivec
TI-994A wrote: Wed Sep 04, 2024 12:58 pm
spikey wrote: Wed Sep 04, 2024 12:40 pm...turning a system event into a custom event by using #PB_EventType_LeftClick as an argument to PostEvent. By then specifying the data parameter too you're distorting both of these facilities slightly from their originally conceived purpose.
PureBasic Manual wrote:PostEvent()
Syntax: Result = PostEvent(Event [, Window, Object [, Type [, Data]]])
PureBasic allows the use of their own native events and event types in the
PostEvent() function. This would be most useful for simulating UI events.
Nevertheless, in my example, the PostEvent() function
(with the native event, event type, and custom data) is working well, without issue.
It is the system-triggered event that is causing the issue; where its EventData() is not null when it should be.
I would think it may actually be in an undefined state. If the event is not acustom one you don't try to interpret the EventData(). If it is a custom event you would interpret it in accordance with that events specification.
Re: How to check if EventData() is defined?
Posted: Wed Sep 04, 2024 4:54 pm
by Fred
The canvas use the 'Data' field of the event to pass an object to a structure to get more info later (like MouseX, MouseY, etc.). It's not a warranty than the EventData() will be null for all PB events, it's only valid when documented. In EventData(), it's written:
"Get the data associated with the current event. The event needs to be a custom event sent with PostEvent()."
we may be could add more precision:
"Get the data associated with the current event. The event needs to be a custom event (not a native PureBasic event) sent with PostEvent()."
Re: How to check if EventData() is defined?
Posted: Wed Sep 04, 2024 5:18 pm
by TI-994A
Fred wrote: Wed Sep 04, 2024 4:54 pm...It's not a warranty than the EventData() will be null for all PB events, it's only valid when documented...
Alright; good to know, Fred. Thank you for chiming in and confirming the matter.
Perhaps best to tweak the descriptions in both the
PostEvent() and
EventData() entries of the manual to reflect this.