forked from trip-zip/somewm
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathevent_queue.h
More file actions
180 lines (152 loc) · 6.37 KB
/
Copy pathevent_queue.h
File metadata and controls
180 lines (152 loc) · 6.37 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
/*
* event_queue.h - Batched event queue for deferred signal dispatch
*
* Replaces synchronous C-to-Lua signal emission with frame-boundary
* delivery. C code queues events during event handling; the drain
* function dispatches them to Lua at defined sync points.
*/
#ifndef EVENT_QUEUE_H
#define EVENT_QUEUE_H
#include <stdbool.h>
#include <stdint.h>
#include <lua.h>
struct lua_class_t;
/* Signal name IDs - avoid string allocation per event.
* Add new entries as signals are converted from synchronous to queued. */
enum {
/* Property signals (informational, 0 args unless noted) */
SIG_PROPERTY_GEOMETRY,
SIG_PROPERTY_POSITION,
SIG_PROPERTY_SIZE,
SIG_PROPERTY_X,
SIG_PROPERTY_Y,
SIG_PROPERTY_WIDTH,
SIG_PROPERTY_HEIGHT,
/* Focus signals */
SIG_PROPERTY_ACTIVE, /* 1 arg: bool */
SIG_FOCUS,
SIG_UNFOCUS,
SIG_CLIENT_FOCUS, /* global */
SIG_CLIENT_UNFOCUS, /* global */
/* Mouse signals */
SIG_MOUSE_ENTER,
SIG_MOUSE_LEAVE,
SIG_MOUSE_MOVE, /* 2 args: local x, y - coalesced per object */
/* Lifecycle signals */
SIG_LIST, /* class-level, 0 args */
SIG_SWAPPED, /* 2 args: other object + is_source bool */
/* Request signals (fire-and-forget, C doesn't check response) */
SIG_REQUEST_ACTIVATE, /* 1-2 args: context [, hints] - also used by systray items */
SIG_REQUEST_URGENT, /* 1 arg: bool */
SIG_REQUEST_TAG, /* 1 arg: tag index or table */
SIG_REQUEST_SELECT, /* 1 arg */
SIG_SYSTRAY_SECONDARY_ACTIVATE, /* 2 args */
SIG_SYSTRAY_CONTEXT_MENU, /* 2 args */
SIG_SYSTRAY_SCROLL, /* 2 args */
/* Global geometry signal */
SIG_CLIENT_PROPERTY_GEOMETRY, /* global */
/* Output and screen change signals */
SIG_PROPERTY_ENABLED,
SIG_PROPERTY_SCALE,
SIG_PROPERTY_TRANSFORM,
SIG_PROPERTY_MODE,
SIG_PROPERTY_ADAPTIVE_SYNC,
SIG_PROPERTY_SCREEN,
SIG_PROPERTY_WORKAREA, /* 1 arg: old workarea */
SIG_PROPERTY_VIEWPORTS, /* class-level, 1 arg: viewports table */
SIG_PRIMARY_CHANGED,
SIG_OUTPUT_ADDED, /* class-level, 1 arg: output */
/* Layer-shell surface property signals */
SIG_PROPERTY_LAYER,
SIG_PROPERTY_ANCHOR,
SIG_PROPERTY_EXCLUSIVE_ZONE,
SIG_PROPERTY_KEYBOARD_INTERACTIVE,
SIG_PROPERTY_MARGIN,
/* Global one-off signals */
SIG_XKB_MAP_CHANGED,
SIG_XKB_GROUP_CHANGED,
SIG_IDLE_STOP,
SIG_DPMS_ON,
SIG_SPAWN_TIMEOUT, /* 1 arg: {id=token} */
SIG_SPAWN_COMPLETED, /* 1 arg: {id=token} */
SIG_SWITCH_TOGGLE, /* 1 arg: {device_name, type, state} */
SIG_SCREEN_FOCUS,
SIG_CLIENT_MAP,
SIG_CLIENT_UNMAP,
/* Placeholder for future conversions */
SIG_COUNT
};
/* Event types */
enum {
EVENT_OBJECT, /* Signal on a specific Lua object */
EVENT_CLASS, /* Signal on a Lua class */
EVENT_GLOBAL, /* Signal on the awesome global */
};
/* A single queued event */
typedef struct {
uint8_t event_type; /* EVENT_OBJECT, EVENT_CLASS, EVENT_GLOBAL */
uint16_t signal_id; /* SIG_* enum value */
int object_ref; /* luaL_ref to target object (LUA_NOREF for globals) */
int nargs; /* Number of arguments captured */
int args_ref; /* luaL_ref to args table (LUA_NOREF if 0 args) */
struct lua_class_t *class_ptr;/* Class for EVENT_CLASS (NULL otherwise) */
} some_event_t;
/* Queue a 0-arg signal on an object (fast path). Used for property
* signals and other 0-arg object signals like focus, unfocus,
* mouse::enter, mouse::leave.
*
* Stack: reads the object at `obj_ud`; leaves the caller's stack
* unchanged. The caller is responsible for popping the object
* afterward if they no longer need it. */
void some_event_queue_signal0(lua_State *L, int obj_ud,
uint16_t signal_id);
/* Queue a signal with arguments on an object.
*
* Stack: expects the object at `obj_ud` and exactly `nargs` argument
* values on top of the stack. Consumes the nargs (pops them); leaves
* the object at `obj_ud` untouched. The caller is responsible for
* popping the object afterward.
*
* Example (1 arg):
* luaA_object_push(L, c); // [..., c]
* lua_pushboolean(L, true); // [..., c, true]
* some_event_queue_signal(L, -2, SIG_PROPERTY_ACTIVE, 1);
* // [..., c] (arg popped, c remains)
* lua_pop(L, 1); // [...] (caller pops c) */
void some_event_queue_signal(lua_State *L, int obj_ud,
uint16_t signal_id, int nargs);
/* Queue a global signal (no object) */
void some_event_queue_global(uint16_t signal_id);
/* Queue a global signal carrying the top nargs stack values as arguments.
* Pops the nargs values from the caller's stack. */
void some_event_queue_global_args(lua_State *L, uint16_t signal_id, int nargs);
/* Queue a global signal carrying one table argument built from alternating
* key/value string pairs (nargs counts the varargs, so pairs = nargs / 2),
* mirroring luaA_emit_signal_global_with_table. */
void some_event_queue_global_with_table(uint16_t signal_id, int nargs, ...);
/* Queue a class-level signal (e.g., client "list"). */
void some_event_queue_class(struct lua_class_t *class_ptr, uint16_t signal_id);
/* Queue a class-level signal carrying the top nargs stack values as
* arguments. Pops the nargs values from the caller's stack. */
void some_event_queue_class_args(lua_State *L, struct lua_class_t *class_ptr,
uint16_t signal_id, int nargs);
/* Queue a mouse::move with coalescing (updates existing if same object).
*
* Stack: reads the object at `obj_ud`; leaves the caller's stack
* unchanged. The caller is responsible for popping the object. */
void some_event_queue_move(lua_State *L, int obj_ud,
int local_x, int local_y);
/* Drain: dispatch all queued events to Lua, then clear */
void some_event_queue_drain(lua_State *L);
/* Check if queue has pending events */
bool some_event_queue_pending(void);
/* Init/cleanup */
void some_event_queue_init(void);
void some_event_queue_wipe(void);
/* Drop pending events, releasing their refs against L, the state that owns
* them. Pass NULL after a state swap, where there is nothing left to unref
* against. Letting the events survive into the new state would be a
* correctness bug: their registry refs are integer slot indices, and the same
* integers point at unrelated slots in the new registry. */
void some_event_queue_reset(lua_State *L);
#endif /* EVENT_QUEUE_H */