@@ -9,7 +9,7 @@ use crate::framework::itest;
9
9
use godot:: builtin:: { GString , Signal , StringName } ;
10
10
use godot:: classes:: { Object , RefCounted } ;
11
11
use godot:: meta:: ToGodot ;
12
- use godot:: obj:: { Base , Gd , NewAlloc , NewGd , WithBaseField , WithSignals } ;
12
+ use godot:: obj:: { Base , Gd , InstanceId , NewAlloc , NewGd , WithSignals } ;
13
13
use godot:: register:: { godot_api, GodotClass } ;
14
14
use godot:: sys;
15
15
use godot:: sys:: Global ;
@@ -21,21 +21,21 @@ fn signal_basic_connect_emit() {
21
21
let mut emitter = Emitter :: new_alloc ( ) ;
22
22
let receiver = Receiver :: new_alloc ( ) ;
23
23
24
- let args = [
25
- vec ! [ ] ,
26
- vec ! [ 987 . to_variant( ) ] ,
27
- vec ! [ receiver. to_variant( ) , SIGNAL_ARG_STRING . to_variant( ) ] ,
28
- ] ;
24
+ emitter. connect ( "signal_unit" , & receiver. callable ( "receive_unit" ) ) ;
25
+ emitter. emit_signal ( "signal_unit" , & [ ] ) ;
26
+ assert_eq ! ( receiver. bind( ) . last_received( ) , LastReceived :: Unit ) ;
29
27
30
- for ( i , arg ) in args . iter ( ) . enumerate ( ) {
31
- let signal_name = format ! ( "emitter_{i}" ) ;
32
- let receiver_name = format ! ( "receiver_{i}" ) ;
28
+ emitter . connect ( "signal_int" , & receiver . callable ( "receive_int" ) ) ;
29
+ emitter . emit_signal ( "signal_int" , & [ 1278 . to_variant ( ) ] ) ;
30
+ assert_eq ! ( receiver . bind ( ) . last_received ( ) , LastReceived :: Int ( 1278 ) ) ;
33
31
34
- emitter. connect ( & signal_name, & receiver. callable ( & receiver_name) ) ;
35
- emitter. emit_signal ( & signal_name, arg) ;
36
-
37
- assert ! ( receiver. bind( ) . used[ i] . get( ) ) ;
38
- }
32
+ let emitter_variant = emitter. to_variant ( ) ;
33
+ emitter. connect ( "signal_obj" , & receiver. callable ( "receive_obj" ) ) ;
34
+ emitter. emit_signal ( "signal_obj" , & [ emitter_variant] ) ;
35
+ assert_eq ! (
36
+ receiver. bind( ) . last_received( ) ,
37
+ LastReceived :: Object ( emitter. instance_id( ) )
38
+ ) ;
39
39
40
40
receiver. free ( ) ;
41
41
emitter. free ( ) ;
@@ -59,7 +59,11 @@ fn signal_symbols_internal() {
59
59
assert_eq ! ( tracker. get( ) , 1234 , "Emit failed (closure)" ) ;
60
60
61
61
// Check that instance method is invoked.
62
- assert_eq ! ( emitter. bind( ) . last_received, 1234 , "Emit failed (method)" ) ;
62
+ assert_eq ! (
63
+ emitter. bind( ) . last_received_int,
64
+ 1234 ,
65
+ "Emit failed (method)"
66
+ ) ;
63
67
64
68
// Check that static function is invoked.
65
69
assert_eq ! (
@@ -76,7 +80,7 @@ fn signal_symbols_internal() {
76
80
#[ itest]
77
81
fn signal_symbols_external ( ) {
78
82
let emitter = Emitter :: new_alloc ( ) ;
79
- let mut sig = emitter. signals ( ) . emitter_1 ( ) ;
83
+ let mut sig = emitter. signals ( ) . signal_int ( ) ;
80
84
81
85
// Local function; deliberately use a !Send type.
82
86
let tracker = Rc :: new ( Cell :: new ( 0 ) ) ;
@@ -92,7 +96,7 @@ fn signal_symbols_external() {
92
96
93
97
// Connect to other object.
94
98
let receiver = Receiver :: new_alloc ( ) ;
95
- sig. connect_obj ( & receiver, Receiver :: receiver_1_mut ) ;
99
+ sig. connect_obj ( & receiver, Receiver :: receive_int_mut ) ;
96
100
97
101
// Emit signal (now via tuple).
98
102
sig. emit_tuple ( ( 987 , ) ) ;
@@ -101,11 +105,16 @@ fn signal_symbols_external() {
101
105
assert_eq ! ( tracker. get( ) , 987 , "Emit failed (closure)" ) ;
102
106
103
107
// Check that instance method is invoked.
104
- assert_eq ! ( emitter. bind( ) . last_received, 987 , "Emit failed (method)" ) ;
108
+ assert_eq ! (
109
+ emitter. bind( ) . last_received_int,
110
+ 987 ,
111
+ "Emit failed (method)"
112
+ ) ;
105
113
106
114
// Check that *other* instance method is invoked.
107
- assert ! (
108
- receiver. bind( ) . used[ 1 ] . get( ) ,
115
+ assert_eq ! (
116
+ receiver. bind( ) . last_received( ) ,
117
+ LastReceived :: IntMut ( 987 ) ,
109
118
"Emit failed (other object method)"
110
119
) ;
111
120
@@ -118,7 +127,7 @@ fn signal_symbols_external() {
118
127
#[ itest]
119
128
fn signal_symbols_external_builder ( ) {
120
129
let emitter = Emitter :: new_alloc ( ) ;
121
- let mut sig = emitter. signals ( ) . emitter_1 ( ) ;
130
+ let mut sig = emitter. signals ( ) . signal_int ( ) ;
122
131
123
132
// Self-modifying method.
124
133
sig. connect_builder ( )
@@ -130,14 +139,14 @@ fn signal_symbols_external_builder() {
130
139
let receiver_mut = Receiver :: new_alloc ( ) ;
131
140
sig. connect_builder ( )
132
141
. object ( & receiver_mut)
133
- . method_mut ( Receiver :: receiver_1_mut )
142
+ . method_mut ( Receiver :: receive_int_mut )
134
143
. done ( ) ;
135
144
136
145
// Connect to yet another object, immutable receiver.
137
146
let receiver_immut = Receiver :: new_alloc ( ) ;
138
147
sig. connect_builder ( )
139
148
. object ( & receiver_immut)
140
- . method_immut ( Receiver :: receiver_1 )
149
+ . method_immut ( Receiver :: receive_int )
141
150
. done ( ) ;
142
151
143
152
let tracker = Rc :: new ( Cell :: new ( 0 ) ) ;
@@ -156,20 +165,22 @@ fn signal_symbols_external_builder() {
156
165
157
166
// Check that self instance method (mut) is invoked.
158
167
assert_eq ! (
159
- emitter. bind( ) . last_received ,
168
+ emitter. bind( ) . last_received_int ,
160
169
552 ,
161
170
"Emit failed (mut method)"
162
171
) ;
163
172
164
173
// Check that *other* instance method is invoked.
165
- assert ! (
166
- receiver_immut. bind( ) . used[ 1 ] . get( ) ,
174
+ assert_eq ! (
175
+ receiver_immut. bind( ) . last_received( ) ,
176
+ LastReceived :: Int ( 552 ) ,
167
177
"Emit failed (other object, immut method)"
168
178
) ;
169
179
170
180
// Check that *other* instance method is invoked.
171
- assert ! (
172
- receiver_mut. bind( ) . used[ 1 ] . get( ) ,
181
+ assert_eq ! (
182
+ receiver_mut. bind( ) . last_received( ) ,
183
+ LastReceived :: IntMut ( 552 ) ,
173
184
"Emit failed (other object, mut method)"
174
185
) ;
175
186
@@ -187,7 +198,7 @@ fn signal_symbols_sync() {
187
198
use std:: sync:: { Arc , Mutex } ;
188
199
189
200
let emitter = Emitter :: new_alloc ( ) ;
190
- let mut sig = emitter. signals ( ) . emitter_1 ( ) ;
201
+ let mut sig = emitter. signals ( ) . signal_int ( ) ;
191
202
192
203
let sync_tracker = Arc :: new ( Mutex :: new ( 0 ) ) ;
193
204
{
@@ -239,25 +250,25 @@ static LAST_STATIC_FUNCTION_ARG: Global<i64> = Global::default();
239
250
struct Emitter {
240
251
_base : Base < Object > ,
241
252
#[ cfg( since_api = "4.2" ) ]
242
- last_received : i64 ,
253
+ last_received_int : i64 ,
243
254
}
244
255
245
256
#[ godot_api]
246
257
impl Emitter {
247
258
#[ signal]
248
- fn emitter_0 ( ) ;
259
+ fn signal_unit ( ) ;
249
260
250
261
#[ signal]
251
- fn emitter_1 ( arg1 : i64 ) ;
262
+ fn signal_int ( arg1 : i64 ) ;
252
263
253
264
#[ signal]
254
- fn emitter_2 ( arg1 : Gd < Object > , arg2 : GString ) ;
265
+ fn signal_obj ( arg1 : Gd < Object > , arg2 : GString ) ;
255
266
256
267
#[ func]
257
268
fn self_receive ( & mut self , arg1 : i64 ) {
258
269
#[ cfg( since_api = "4.2" ) ]
259
270
{
260
- self . last_received = arg1;
271
+ self . last_received_int = arg1;
261
272
}
262
273
}
263
274
@@ -270,54 +281,66 @@ impl Emitter {
270
281
271
282
#[ cfg( since_api = "4.2" ) ]
272
283
fn connect_signals_internal ( & mut self , tracker : Rc < Cell < i64 > > ) {
273
- let mut sig = self . signals ( ) . emitter_1 ( ) ;
284
+ let mut sig = self . signals ( ) . signal_int ( ) ;
274
285
sig. connect_self ( Self :: self_receive) ;
275
286
sig. connect ( Self :: self_receive_static) ;
276
287
sig. connect ( move |i| tracker. set ( i) ) ;
277
288
}
278
289
279
290
#[ cfg( since_api = "4.2" ) ]
280
291
fn emit_signals_internal ( & mut self ) {
281
- self . signals ( ) . emitter_1 ( ) . emit ( 1234 ) ;
292
+ self . signals ( ) . signal_int ( ) . emit ( 1234 ) ;
282
293
}
283
294
}
284
295
296
+ // ----------------------------------------------------------------------------------------------------------------------------------------------
297
+
298
+ #[ derive( Default , Copy , Clone , Eq , PartialEq , Debug ) ]
299
+ enum LastReceived {
300
+ #[ default]
301
+ Nothing ,
302
+ Unit ,
303
+ Int ( i64 ) ,
304
+ IntMut ( i64 ) ,
305
+ Object ( InstanceId ) ,
306
+ }
307
+
285
308
#[ derive( GodotClass ) ]
286
309
#[ class( init, base=Object ) ]
287
310
struct Receiver {
288
- used : [ Cell < bool > ; 3 ] ,
311
+ last_received : Cell < LastReceived > ,
289
312
base : Base < Object > ,
290
313
}
291
-
292
314
#[ godot_api]
293
315
impl Receiver {
316
+ fn last_received ( & self ) -> LastReceived {
317
+ self . last_received . get ( )
318
+ }
319
+
320
+ // Note: asserting inside #[func] will be caught by FFI layer and not cause a call-site panic, thus not fail the test.
321
+ // Therefore, store received values and check them manually in the test.
322
+
294
323
#[ func]
295
- fn receiver_0 ( & self ) {
296
- self . used [ 0 ] . set ( true ) ;
324
+ fn receive_unit ( & self ) {
325
+ self . last_received . set ( LastReceived :: Unit ) ;
297
326
}
298
327
299
328
#[ func]
300
- fn receiver_1 ( & self , arg1 : i64 ) {
301
- self . used [ 1 ] . set ( true ) ;
302
- assert_eq ! ( arg1, 987 ) ;
329
+ fn receive_int ( & self , arg1 : i64 ) {
330
+ self . last_received . set ( LastReceived :: Int ( arg1) ) ;
303
331
}
304
332
305
- fn receiver_1_mut ( & mut self , arg1 : i64 ) {
306
- self . used [ 1 ] . set ( true ) ;
307
- assert_eq ! ( arg1, 987 ) ;
333
+ fn receive_int_mut ( & mut self , arg1 : i64 ) {
334
+ self . last_received . set ( LastReceived :: IntMut ( arg1) ) ;
308
335
}
309
336
310
337
#[ func]
311
- fn receiver_2 ( & self , arg1 : Gd < Object > , arg2 : GString ) {
312
- assert_eq ! ( self . base( ) . clone( ) , arg1) ;
313
- assert_eq ! ( SIGNAL_ARG_STRING , arg2. to_string( ) ) ;
314
-
315
- self . used [ 2 ] . set ( true ) ;
338
+ fn receive_obj ( & self , obj : Gd < Object > ) {
339
+ self . last_received
340
+ . set ( LastReceived :: Object ( obj. instance_id ( ) ) ) ;
316
341
}
317
342
}
318
343
319
- const SIGNAL_ARG_STRING : & str = "Signal string arg" ;
320
-
321
344
// ----------------------------------------------------------------------------------------------------------------------------------------------
322
345
// 4.2+ custom callables
323
346
0 commit comments