@@ -11,54 +11,28 @@ pub(crate) fn impl_joined_value(ast: DeriveInput) -> Result<TokenStream> {
11
11
_ => return Err ( "expected struct" . to_string ( ) ) ,
12
12
} ;
13
13
let map_key: Vec < String > = field_ident. iter ( ) . map ( |v| v. to_string ( ) ) . collect ( ) ;
14
- let struct_buffer_ident = format_ident ! ( "__{}Buffers " , struct_ident) ;
14
+ let struct_buffer_ident = format_ident ! ( "__bevy_impulse_{}_Buffers " , struct_ident) ;
15
15
16
16
let impl_buffer_map_layout =
17
- buffer_map_layout ( & struct_ident, & field_ident, & field_type, & map_key) ;
17
+ buffer_map_layout ( & struct_buffer_ident, & field_ident, & field_type, & map_key) ;
18
+ let impl_joined = joined ( & struct_buffer_ident, & struct_ident, & field_ident) ;
18
19
19
20
let gen = quote ! {
20
- #impl_buffer_map_layout
21
-
22
21
impl :: bevy_impulse:: JoinedValue for #struct_ident {
23
22
type Buffers = #struct_buffer_ident;
24
-
25
- fn pull(
26
- buffers: & :: bevy_impulse:: BufferMap ,
27
- session: :: bevy_ecs:: prelude:: Entity ,
28
- world: & mut :: bevy_ecs:: prelude:: World ,
29
- ) -> Result <Self , :: bevy_impulse:: OperationError > {
30
- use :: bevy_impulse:: { ManageBuffer , OrBroken } ;
31
-
32
- #(
33
- let #field_ident = world
34
- . get_entity_mut( buffers. get( #map_key) . or_broken( ) ?. id( ) )
35
- . or_broken( ) ?
36
- . pull_from_buffer:: <#field_type>( session) ?;
37
- ) *
38
-
39
- Ok ( Self {
40
- #(
41
- #field_ident
42
- ) , *
43
- } )
44
- }
45
23
}
46
24
25
+ #[ derive( Clone ) ]
26
+ #[ allow( non_camel_case_types) ]
47
27
struct #struct_buffer_ident {
48
28
#(
49
- #field_ident: :: bevy_impulse:: Buffer <#field_type>
50
- ) , *
29
+ #field_ident: :: bevy_impulse:: Buffer <#field_type>,
30
+ ) *
51
31
}
52
32
53
- impl From <#struct_buffer_ident> for :: bevy_impulse:: BufferMap {
54
- fn from( value: #struct_buffer_ident) -> Self {
55
- let mut buffers = :: bevy_impulse:: BufferMap :: default ( ) ;
56
- #(
57
- buffers. insert( std:: borrow:: Cow :: Borrowed ( #map_key) , value. #field_ident) ;
58
- ) *
59
- buffers
60
- }
61
- }
33
+ #impl_buffer_map_layout
34
+
35
+ #impl_joined
62
36
} ;
63
37
64
38
Ok ( gen. into ( ) )
@@ -86,103 +60,49 @@ fn buffer_map_layout(
86
60
) -> proc_macro2:: TokenStream {
87
61
quote ! {
88
62
impl :: bevy_impulse:: BufferMapLayout for #struct_ident {
89
- fn is_compatible( buffers: & BufferMap ) -> Result <( ) , :: bevy_impulse:: IncompatibleLayout > {
90
- let mut compatibility = :: bevy_impulse:: IncompatibleLayout :: default ( ) ;
91
- #(
92
- compatibility. require_buffer:: <#field_type>( #map_key, buffers) ;
93
- ) *
94
- compatibility. into_result( )
63
+ fn buffer_list( & self ) -> :: smallvec:: SmallVec <[ AnyBuffer ; 8 ] > {
64
+ use smallvec:: smallvec;
65
+ smallvec![ #(
66
+ self . #field_ident. as_any_buffer( ) ,
67
+ ) * ]
95
68
}
96
69
97
- fn buffered_count(
98
- buffers: & :: bevy_impulse:: BufferMap ,
99
- session: :: bevy_ecs:: prelude:: Entity ,
100
- world: & :: bevy_ecs:: prelude:: World ,
101
- ) -> Result <usize , :: bevy_impulse:: OperationError > {
102
- use :: bevy_impulse:: { InspectBuffer , OrBroken } ;
103
-
104
- #(
105
- let #field_ident = world
106
- . get_entity( buffers. get( #map_key) . or_broken( ) ?. id( ) )
107
- . or_broken( ) ?
108
- . buffered_count:: <#field_type>( session) ?;
109
- ) *
110
-
111
- Ok ( [ #( #field_ident ) , * ]
112
- . iter( )
113
- . min( )
114
- . copied( )
115
- . unwrap_or( 0 ) )
116
- }
117
-
118
- fn ensure_active_session(
119
- buffers: & :: bevy_impulse:: BufferMap ,
120
- session: :: bevy_ecs:: prelude:: Entity ,
121
- world: & mut :: bevy_ecs:: prelude:: World ,
122
- ) -> :: bevy_impulse:: OperationResult {
123
- use :: bevy_impulse:: { ManageBuffer , OrBroken } ;
124
-
70
+ fn try_from_buffer_map( buffers: & :: bevy_impulse:: BufferMap ) -> Result <Self , :: bevy_impulse:: IncompatibleLayout > {
71
+ let mut compatibility = :: bevy_impulse:: IncompatibleLayout :: default ( ) ;
125
72
#(
126
- world
127
- . get_entity_mut( buffers. get( #map_key) . or_broken( ) ?. id( ) )
128
- . or_broken( ) ?
129
- . ensure_session:: <#field_type>( session) ?;
73
+ let #field_ident = if let Ok ( buffer) = compatibility. require_message_type:: <#field_type>( #map_key, buffers) {
74
+ buffer
75
+ } else {
76
+ return Err ( compatibility) ;
77
+ } ;
130
78
) *
131
79
132
- Ok ( ( ) )
80
+ Ok ( Self { #(
81
+ #field_ident,
82
+ ) * } )
133
83
}
134
84
}
135
85
}
136
86
}
137
87
138
- pub ( crate ) fn impl_buffer_key_map ( ast : DeriveInput ) -> Result < TokenStream > {
139
- let struct_ident = ast. ident ;
140
- let ( field_ident, field_type) : ( Vec < Ident > , Vec < Type > ) = match ast. data {
141
- syn:: Data :: Struct ( data) => get_fields_map ( data. fields ) ?. into_iter ( ) . unzip ( ) ,
142
- _ => return Err ( "expected struct" . to_string ( ) ) ,
143
- } ;
144
- let map_key: Vec < String > = field_ident. iter ( ) . map ( |v| v. to_string ( ) ) . collect ( ) ;
145
-
146
- let impl_buffer_map_layout =
147
- buffer_map_layout ( & struct_ident, & field_ident, & field_type, & map_key) ;
148
-
149
- // FIXME(koonpeng): `create_key` does not allow failure and we can't guarantee that the buffer
150
- // from the buffer map is valid.
151
- let gen = quote ! {
152
- impl :: bevy_impulse:: BufferKeyMap for #struct_ident {
153
- fn add_accessor( buffers: & :: bevy_impulse:: BufferMap , accessor: :: bevy_ecs:: prelude:: Entity , world: & mut :: bevy_ecs:: prelude:: World ) -> :: bevy_impulse:: OperationResult {
154
- use :: bevy_impulse:: { Accessed , OrBroken } ;
88
+ fn joined (
89
+ struct_ident : & Ident ,
90
+ item_struct_ident : & Ident ,
91
+ field_ident : & Vec < Ident > ,
92
+ ) -> proc_macro2:: TokenStream {
93
+ quote ! {
94
+ impl :: bevy_impulse:: Joined for #struct_ident {
95
+ type Item = #item_struct_ident;
155
96
97
+ fn pull( & self , session: :: bevy_ecs:: prelude:: Entity , world: & mut :: bevy_ecs:: prelude:: World ) -> Result <Self :: Item , :: bevy_impulse:: OperationError > {
156
98
#(
157
- buffers . get ( #map_key ) . or_broken ( ) ? . add_accessor ( accessor , world) ?;
99
+ let #field_ident = self . #field_ident . pull ( session , world) ?;
158
100
) *
159
101
160
- Ok ( ( ) )
161
- }
162
-
163
- fn create_key( buffers: & :: bevy_impulse:: BufferMap , builder: & :: bevy_impulse:: BufferKeyBuilder ) -> Self {
164
- use :: bevy_impulse:: { Accessed , OrBroken } ;
165
-
166
- Self { #(
167
- #field_ident: buffers. get( #map_key) . unwrap( ) . create_key( builder) . try_into( ) . unwrap( ) ,
168
- ) * }
169
- }
170
-
171
- fn deep_clone_key( & self ) -> Self {
172
- Self { #(
173
- #field_ident: self . #field_ident. deep_clone( ) ,
174
- ) * }
175
- }
176
-
177
- fn is_key_in_use( & self ) -> bool {
178
- #(
179
- self . #field_ident. is_in_use( )
180
- ) ||*
102
+ Ok ( Self :: Item { #(
103
+ #field_ident,
104
+ ) * } )
181
105
}
182
106
}
183
-
184
- #impl_buffer_map_layout
185
- } ;
186
-
187
- Ok ( gen. into ( ) )
107
+ }
188
108
}
0 commit comments