1use {
2 crate::{
3 makepad_live_compiler::*,
4 cx::Cx,
5 }
6};
7
8pub use crate::live_cx::LiveBody;
9
10pub trait LiveHook {
11 fn before_live_design(_cx:&mut Cx){}
12
13 fn apply_value_unknown(&mut self, cx: &mut Cx, _apply_from: ApplyFrom, index: usize, nodes: &[LiveNode]) -> usize {
14 if !nodes[index].origin.node_has_prefix() {
15 cx.apply_error_no_matching_field(live_error_origin!(), index, nodes);
16 }
17 nodes.skip_node(index)
18 }
19
20 fn apply_value_instance(&mut self, _cx: &mut Cx, _apply_from: ApplyFrom, index: usize, nodes: &[LiveNode]) -> usize {
21 nodes.skip_node(index)
22 }
23
24 fn skip_apply(&mut self, _cx: &mut Cx, _apply_from: ApplyFrom, _index: usize, _nodes: &[LiveNode])->Option<usize>{None}
25 fn before_apply(&mut self, _cx: &mut Cx, _apply_from: ApplyFrom, _index: usize, _nodes: &[LiveNode]){}
26 fn after_apply(&mut self, _cx: &mut Cx, _apply_from: ApplyFrom, _index: usize, _nodes: &[LiveNode]) {}
27 fn after_apply_from(&mut self, cx: &mut Cx, apply_from: ApplyFrom) {
28 match apply_from{
29 ApplyFrom::NewFromDoc{..}=>self.after_new_from_doc(cx),
30 _=>()
31 }
32 }
33 fn after_new_from_doc(&mut self, _cx:&mut Cx){}
34 fn after_new_before_apply(&mut self, _cx: &mut Cx) {}
35}
36
37pub trait LiveHookDeref {
38 fn deref_before_apply(&mut self, _cx: &mut Cx, _apply_from: ApplyFrom, _index: usize, _nodes: &[LiveNode]){}
39 fn deref_after_apply(&mut self, _cx: &mut Cx, _apply_from: ApplyFrom, _index: usize, _nodes: &[LiveNode]){}
40}
41
42pub trait LiveNew: LiveApply {
43 fn new(cx: &mut Cx) -> Self;
44
45 fn live_design_with(_cx: &mut Cx) {}
46
47 fn live_type_info(cx: &mut Cx) -> LiveTypeInfo;
48
49 fn new_apply(cx: &mut Cx, from: ApplyFrom, index: usize, nodes: &[LiveNode]) -> Self where Self: Sized {
50 let mut ret = Self::new(cx);
51 ret.apply(cx, from, index, nodes);
52 ret
53 }
54
55 fn new_apply_mut_index(cx: &mut Cx, from: ApplyFrom, index: &mut usize, nodes: &[LiveNode]) -> Self where Self: Sized {
56 let mut ret = Self::new(cx);
57 *index = ret.apply(cx, from, *index, nodes);
58 ret
59 }
60
61 fn new_from_ptr(cx: &mut Cx, live_ptr: Option<LivePtr>) -> Self where Self: Sized {
62 let mut ret = Self::new(cx);
63 if let Some(live_ptr) = live_ptr{
64 cx.get_nodes_from_live_ptr(live_ptr, |cx, file_id, index, nodes|{
65 ret.apply(cx, ApplyFrom::NewFromDoc {file_id}, index, nodes)
66 });
67 }
68 return ret
69 }
70
71 fn new_main(cx: &mut Cx) -> Self where Self: Sized {
72 let lti = Self::live_type_info(cx);
73 {
74 let live_registry_rc = cx.live_registry.clone();
75 let mut live_registry = live_registry_rc.borrow_mut();
76 live_registry.main_module = Some((lti.module_id, lti.type_name));
77 }
78 Self::new_from_module(cx, lti.module_id, lti.type_name).unwrap()
79 }
80
81 fn update_main(&mut self, cx:&mut Cx){
82 let (module_id, id) = {
83 let live_registry_rc = cx.live_registry.clone();
84 let live_registry = live_registry_rc.borrow_mut();
85 live_registry.main_module.unwrap()
86 };
87 self.update_from_module(cx, module_id, id);
88 }
89
90 fn new_local(cx: &mut Cx) -> Self where Self: Sized {
91 let lti = Self::live_type_info(cx);
92 Self::new_from_module(cx, lti.module_id, lti.type_name).unwrap()
93 }
94
95 fn new_from_module(cx: &mut Cx, module_id: LiveModuleId, id: LiveId) -> Option<Self> where Self: Sized {
96 let live_registry_rc = cx.live_registry.clone();
97 let live_registry = live_registry_rc.borrow();
98 if let Some(file_id) = live_registry.module_id_to_file_id.get(&module_id) {
99 let file = live_registry.file_id_to_file(*file_id);
100 if let Some(index) = file.expanded.nodes.child_by_name(0, id.as_instance()) {
101 let mut ret = Self::new(cx);
102 ret.apply(cx, ApplyFrom::NewFromDoc {file_id: *file_id}, index, &file.expanded.nodes);
103 return Some(ret)
104 }
105 }
106 None
107 }
108
109 fn update_from_module(&mut self, cx: &mut Cx, module_id: LiveModuleId, id: LiveId) {
110 let live_registry_rc = cx.live_registry.clone();
111 let live_registry = live_registry_rc.borrow();
112 if let Some(file_id) = live_registry.module_id_to_file_id.get(&module_id) {
113 let file = live_registry.file_id_to_file(*file_id);
114 if let Some(index) = file.expanded.nodes.child_by_name(0, id.as_instance()) {
115
116 self.apply(cx, ApplyFrom::UpdateFromDoc {file_id: *file_id}, index, &file.expanded.nodes);
117 }
118 }
119 }
120}
121
122pub trait ToLiveValue {
123 fn to_live_value(&self) -> LiveValue;
124}
125
126pub trait LiveApplyValue {
127 fn apply_value(&mut self, cx: &mut Cx, from: ApplyFrom, index: usize, nodes: &[LiveNode]) -> usize;
128}
129
130pub trait LiveApply {
131 fn apply(&mut self, cx: &mut Cx, from: ApplyFrom, index: usize, nodes: &[LiveNode]) -> usize;
132
133 fn apply_over(&mut self, cx: &mut Cx, nodes: &[LiveNode]) {
134 self.apply(cx, ApplyFrom::ApplyOver, 0, nodes);
135 }
136}
137
138pub trait LiveRead{
139 fn live_read_to(&self, id:LiveId, out:&mut Vec<LiveNode>);
140 fn live_read(&self)->Vec<LiveNode>{
141 let mut out = Vec::new();
142 self.live_read_to(LiveId(0),&mut out);
143 out
144 }
145
146}
147
148impl<T, const N:usize> LiveRead for [T;N] where T: LiveRead {
149 fn live_read_to(&self, id:LiveId, out:&mut Vec<LiveNode>){
150 out.open_array(id);
151 for i in 0..N{
152 self[i].live_read_to(LiveId(i as u64), out);
153 }
154 out.close();
155 }
156}
157
158#[derive(Debug, Clone, Copy)]
159pub enum ApplyFrom {
160 NewFromDoc {file_id: LiveFileId}, UpdateFromDoc {file_id: LiveFileId}, New, Animate, AnimatorInit,
166 ApplyOver, }
168
169impl ApplyFrom {
170 pub fn is_from_doc(&self) -> bool {
171 match self {
172 Self::NewFromDoc {..} => true,
173 Self::UpdateFromDoc {..} => true,
174 _ => false
175 }
176 }
177
178 pub fn is_new_from_doc(&self) -> bool {
179 match self {
180 Self::NewFromDoc {..} => true,
181 _ => false
182 }
183 }
184
185 pub fn file_id(&self) -> Option<LiveFileId> {
186 match self {
187 Self::NewFromDoc {file_id} => Some(*file_id),
188 Self::UpdateFromDoc {file_id} => Some(*file_id),
189 _ => None
190 }
191 }
192}
193
194
195impl<T> LiveHook for Option<T> where T: LiveApply + LiveNew + 'static {}
196impl<T> LiveApply for Option<T> where T: LiveApply + LiveNew + 'static {
197 fn apply(&mut self, cx: &mut Cx, from: ApplyFrom, index: usize, nodes: &[LiveNode]) -> usize {
198 if let Some(v) = self {
199 v.apply(cx, from, index, nodes)
200 }
201 else {
202 let mut inner = T::new(cx);
203 let index = inner.apply(cx, from, index, nodes);
204 *self = Some(inner);
205 index
206 }
207 }
208}
209
210impl<T> LiveNew for Option<T> where T: LiveApply + LiveNew + 'static{
211 fn new(_cx: &mut Cx) -> Self {
212 Self::None
213 }
214 fn new_apply(cx: &mut Cx, from: ApplyFrom, index: usize, nodes: &[LiveNode]) -> Self {
215 let mut ret = Self::None;
216 ret.apply(cx, from, index, nodes);
217 ret
218 }
219
220 fn live_type_info(_cx: &mut Cx) -> LiveTypeInfo {
221 T::live_type_info(_cx)
222 }
223}
224
225
226impl<T> LiveHook for Vec<T> where T: LiveApply + LiveNew + 'static {}
227impl<T> LiveApply for Vec<T> where T: LiveApply + LiveNew + 'static {
228 fn apply(&mut self, cx: &mut Cx, from: ApplyFrom, index: usize, nodes: &[LiveNode]) -> usize {
229 self.clear();
231 if nodes[index].is_array(){
232 let mut index = index + 1;
233 loop{
234 if nodes[index].is_close(){
235 index += 1;
236 break;
237 }
238 let mut inner = T::new(cx);
239 index = inner.apply(cx, from, index, nodes);
240 self.push(inner);
241 }
242 index
243 }
244 else{
245 cx.apply_error_expected_array(live_error_origin!(), index, nodes);
246 nodes.skip_node(index)
247 }
248 }
249}
250
251impl<T> LiveNew for Vec<T> where T: LiveApply + LiveNew + 'static{
252 fn new(_cx: &mut Cx) -> Self {
253 Vec::new()
254 }
255 fn new_apply(cx: &mut Cx, from: ApplyFrom, index: usize, nodes: &[LiveNode]) -> Self {
256 let mut ret = Vec::new();
257 ret.apply(cx, from, index, nodes);
258 ret
259 }
260
261 fn live_type_info(_cx: &mut Cx) -> LiveTypeInfo {
262 T::live_type_info(_cx)
263 }
264}
265
266
267impl<T, const N:usize> LiveHook for [T;N] where T: LiveApply + LiveNew + 'static{}
268impl<T, const N:usize> LiveApply for [T;N] where T: LiveApply + LiveNew + 'static {
269 fn apply(&mut self, cx: &mut Cx, from: ApplyFrom, index: usize, nodes: &[LiveNode]) -> usize {
270 if nodes[index].is_array(){
272 let mut index = index + 1;
273 let mut count = 0;
274 loop{
275 if nodes[index].is_close(){
276 index += 1;
277 break;
278 }
279 if count < self.len(){
280 index = self[count].apply(cx, from, index, nodes);
281 count += 1;
282 }
283 else{
284 index = nodes.skip_node(index)
285 }
286 }
287 index
288 }
289 else{
290 cx.apply_error_expected_array(live_error_origin!(), index, nodes);
291 nodes.skip_node(index)
292 }
293 }
294}
295
296impl<T, const N:usize> LiveNew for [T;N] where T: LiveApply + LiveNew + 'static{
297 fn new(cx: &mut Cx) -> Self {
298 std::array::from_fn(|_| T::new(cx))
299 }
300
301 fn new_apply(cx: &mut Cx, from: ApplyFrom, index: usize, nodes: &[LiveNode]) -> Self {
302 let mut ret = Self::new(cx);
303 ret.apply(cx, from, index, nodes);
304 ret
305 }
306
307 fn live_type_info(_cx: &mut Cx) -> LiveTypeInfo {
308 T::live_type_info(_cx)
309 }
310}
311
312
313
314