makepad_live_compiler/
live_node.rs

1use {
2    std::{
3        collections::HashMap,
4        rc::Rc,
5        fmt,
6        ops::{Deref, DerefMut},
7    },
8    crate::{
9        makepad_math::{
10            Vec2,
11            Vec3,
12            Vec4
13        },
14        live_registry::LiveScopeTarget,
15        makepad_live_tokenizer::{LiveId},
16        live_ptr::{LiveModuleId, LivePtr},
17        live_token::{LiveToken, LiveTokenId},
18    }
19};
20
21#[derive(Clone, Debug, PartialEq)]
22pub struct LiveNode { // 40 bytes. Don't really see ways to compress
23    pub origin: LiveNodeOrigin,
24    pub id: LiveId,
25    pub value: LiveValue,
26}
27
28#[derive(Clone, Debug, PartialEq)]
29pub enum LiveValue {
30    None,
31    // string types
32    Str(&'static str),
33    String(Rc<String>),
34    InlineString(InlineString),
35    Dependency(Rc<String>),
36    Bool(bool),
37    Int64(i64),
38    Float32(f32),
39    Float64(f64),
40    Color(u32),
41    Vec2(Vec2),
42    Vec3(Vec3),
43    Vec4(Vec4),
44
45    Id(LiveId),
46    IdPath(Rc<Vec<LiveId>>),
47
48    ExprBinOp(LiveBinOp),
49    ExprUnOp(LiveUnOp),
50    ExprMember(LiveId),
51    ExprCall {ident: LiveId, args: usize},
52     // enum thing
53    BareEnum (LiveId),
54    // tree items
55    Root{id_resolve:Box<HashMap<LiveId,LiveScopeTarget>>},
56    Array,
57    Expr {expand_index: Option<u32>},
58    TupleEnum (LiveId),
59    NamedEnum (LiveId),
60    Object,
61    Clone(LiveId),
62    Class {live_type: LiveType, class_parent: Option<LivePtr>},
63    Close,
64    
65    // shader code and other DSLs
66    DSL {
67        token_start: u32,
68        token_count: u32,
69        expand_index: Option<u32>
70    },
71    Import (Box<LiveImport>),
72}
73
74#[derive(Clone, Debug, PartialEq)]
75pub struct LiveImport{
76    pub module_id: LiveModuleId,
77    pub import_id: LiveId,
78}
79
80#[derive(Debug, Clone, PartialEq)]
81pub struct LiveBinding{
82    pub from: LiveIdPath,
83    pub to: LiveIdPath
84}
85
86#[derive(Debug, Clone, PartialEq)]
87pub struct LiveIdPath(pub Vec<LiveId>);
88
89impl LiveValue {
90    pub fn update_from_live_token(&mut self, token: &LiveToken) -> bool {
91        match self {
92            Self::String(rcstring)  => {
93                if let LiveToken::String(other_rcstring) = token {
94                    *rcstring = other_rcstring.clone();
95                    return true
96                }
97            },
98            Self::Color(o) => if let LiveToken::Color(i) = token {
99                *o = *i;
100                return true
101            },
102            Self::Bool(o) => if let LiveToken::Bool(i) = token {
103                *o = *i;
104                return true
105            },
106            Self::Int64(o) => {
107                if let LiveToken::Int(i) = token {
108                    *o = *i;
109                    return true
110                }
111                if let LiveToken::Float(v) = token {
112                    *self = LiveValue::Float64(*v);
113                    return true
114                }
115            }
116            Self::Float64(o) => {
117                if let LiveToken::Float(i) = token {
118                    *o = *i;
119                    return true
120                }
121                if let LiveToken::Int(v) = token {
122                    *self = LiveValue::Int64(*v);
123                    return true
124                }
125            }
126            Self::Float32(o) => {
127                if let LiveToken::Float(i) = token {
128                    *o = *i as f32;
129                    return true
130                }
131                if let LiveToken::Int(v) = token {
132                    *self = LiveValue::Int64(*v);
133                    return true
134                }
135            }
136            _ => ()
137            
138        }
139        false
140    }
141}
142
143impl LiveNode {
144    
145    pub fn empty() -> Self {
146        Self {
147            origin: LiveNodeOrigin::empty(),
148            id: LiveId(0),
149            value: LiveValue::None
150        }
151    }
152    pub fn from_id_value(id: LiveId, value: LiveValue) -> Self {
153        Self {
154            origin: LiveNodeOrigin::empty(),
155            id,
156            value
157        }
158    }
159    
160    pub fn from_value(value: LiveValue) -> Self {
161        Self {
162            origin: LiveNodeOrigin::empty(),
163            id: LiveId(0),
164            value
165        }
166    }
167    
168    pub fn is_token_id_inside_dsl(&self, other_token: LiveTokenId) -> bool {
169        if let Some(token_id) = self.origin.token_id() {
170            if token_id.file_id() != other_token.file_id() {
171                return false
172            }
173        }
174        else {
175            return false;
176        }
177        match &self.value {
178            LiveValue::DSL {token_start, token_count, ..} => {
179                let token_index = other_token.token_index();
180                token_index as u32 >= *token_start && (token_index as u32) < token_start + token_count
181            }
182            _ => false
183        }
184    }
185    
186    pub fn prop(&self) -> LiveProp {
187        LiveProp(self.id, self.origin.prop_type())
188    }
189    
190}
191
192#[derive(Copy, Clone, Debug)]
193pub struct LiveProp(pub LiveId, pub LivePropType);
194impl LiveProp {
195    pub fn field(id: LiveId) -> Self {Self (id, LivePropType::Field)}
196    pub fn instance(id: LiveId) -> Self {Self (id, LivePropType::Instance)}
197}
198
199pub trait LiveIdAsProp {
200    fn as_field(&self) -> LiveProp;
201    fn as_instance(&self) -> LiveProp;
202}
203
204impl LiveIdAsProp for LiveId {
205    fn as_field(&self) -> LiveProp {LiveProp(*self, LivePropType::Field)}
206    fn as_instance(&self) -> LiveProp {LiveProp(*self, LivePropType::Instance)}
207}
208
209#[derive(Copy, Clone, PartialEq)]
210pub struct LiveNodeOrigin(u64);
211
212impl fmt::Debug for LiveNodeOrigin {
213    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
214        write!(f, "token_id:{:?} first_def:{:?} edit_info:{:?} prop_type:{:?}", self.token_id(), self.first_def(), self.edit_info(), self.prop_type())
215    }
216}
217
218// this layout can be reshuffled and just be made bigger.
219// However it keeps the LiveNode size at 40 bytes which is nice for now.
220
221// 10 bit file id (1024)
222// 18 bit token id (262k tokens, avg tokensize: 5 = 1.25 megs of code used to find original token of property
223
224// 10 bit first def file_id
225// 18 bit first def token_id
226
227// 6 bits (64) edit_info index
228// 1 bit node_has_prefix
229// 2 bits LivePropType
230
231// ok if we are a DSL node then what else do we need. we need a node index pointer.
232
233#[derive(Debug, Clone, Copy, PartialEq)]
234#[repr(usize)]
235pub enum LivePropType {
236    Field = 0,
237    Instance = 1,
238    //Template = 2,
239    Nameless = 3
240}
241
242impl LiveNodeOrigin {
243    pub fn empty() -> Self {
244        Self (0)
245    }
246    
247    pub fn field() -> Self {
248        Self (0).with_prop_type(LivePropType::Field)
249    }
250    
251    pub fn instance() -> Self {
252        Self (0).with_prop_type(LivePropType::Instance)
253    }
254    
255    
256    pub fn from_token_id(token_id: LiveTokenId) -> Self {
257        Self ((token_id.to_bits() as u64) | ((token_id.to_bits() as u64) << 28))
258    }
259    
260    pub fn token_id(&self) -> Option<LiveTokenId> {
261        LiveTokenId::from_bits((self.0 & 0x0fff_ffff) as u32)
262    }
263    
264    
265    pub fn set_first_def(&mut self, token_id: Option<LiveTokenId>) -> &mut Self {
266        if let Some(token_id) = token_id {
267            self.0 = (self.0 & 0xff00_0000_0fff_ffff) | ((token_id.to_bits() as u64) << 28);
268        }
269        self
270    }
271    
272    pub fn first_def(&self) -> Option<LiveTokenId> {
273        LiveTokenId::from_bits(((self.0 >> 28) & 0x0fff_ffff) as u32)
274    }
275    
276    pub fn set_edit_info(&mut self, edit_info: Option<LiveEditInfo>) -> &mut Self {
277        if let Some(edit_info) = edit_info {
278            self.0 = (self.0 & 0xE0FF_FFFF_FFFF_FFFF) | ((edit_info.to_bits() as u64) << 56);
279        }
280        self
281    }
282    
283    pub fn with_edit_info(mut self, edit_info: Option<LiveEditInfo>) -> Self {
284        self.set_edit_info(edit_info);
285        self
286    }
287    
288    pub fn edit_info(&self) -> Option<LiveEditInfo> {
289        LiveEditInfo::from_bits(((self.0 & 0x1f00_0000_0000_0000) >> 56) as u32)
290    }
291    
292    pub fn set_node_has_prefix(&mut self, node_has_prefix: bool) {
293        if node_has_prefix {
294            self.0 |= 0x2000_0000_0000_0000;
295        }
296    }
297    
298    pub fn with_node_has_prefix(mut self, node_has_prefix: bool) -> Self {
299        self.set_node_has_prefix(node_has_prefix);
300        self
301    }
302    
303    pub fn node_has_prefix(&self) -> bool {
304        self.0 & 0x2000_0000_0000_0000 != 0
305    }
306    
307    pub fn with_prop_type(mut self, prop_type: LivePropType) -> Self {
308        self.0 |= (prop_type as u64) << 62; //0x8000_0000_0000_0000;
309        self
310    }
311    
312    pub fn set_prop_type(&mut self, prop_type: LivePropType) {
313        self.0 = (self.0 & (!0xC000_0000_0000_0000)) | ((prop_type as u64) << 62);
314    }
315    
316    pub fn prop_type(&self) -> LivePropType {
317        LivePropType::from_usize(((self.0 & 0xC000_0000_0000_0000) >> 62) as usize)
318    }
319    
320    pub fn has_prop_type(&self, origin: LivePropType) -> bool {
321        (self.0 & 0xC000_0000_0000_0000) >> 62 == origin as u64
322    }
323    
324    pub fn inherit_origin(&mut self, origin: Self) {
325        let edit_info = origin.edit_info();
326        let first_def = origin.first_def();
327        let node_has_prefix = origin.node_has_prefix();
328        self.set_edit_info(edit_info);
329        self.set_first_def(first_def);
330        self.set_node_has_prefix(node_has_prefix);
331    }
332}
333
334impl LivePropType {
335    pub fn from_usize(val: usize) -> Self {
336        match val {
337            0 => Self::Field,
338            1 => Self::Instance,
339            //2 => Self::Template,
340            _ => Self::Nameless
341        }
342    }
343}
344
345pub struct LiveEditInfo(u32);
346
347impl fmt::Debug for LiveEditInfo {
348    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
349        write!(f, "{:?}", self.edit_info_index())
350    }
351}
352
353impl LiveEditInfo {
354    pub fn new(edit_info_index: usize) -> Self {
355        if edit_info_index & 0xf != 0 || edit_info_index > 0x3e0 {
356            panic!();
357        }
358        LiveEditInfo(((edit_info_index as u32) >> 4) + 1)
359    }
360    
361    pub fn edit_info_index(&self) -> usize {
362        (((self.0) as usize - 1) << 4) & 0x3f0
363    }
364    
365    pub fn to_bits(&self) -> u32 {self.0}
366    pub fn from_bits(v: u32) -> Option<Self> {
367        if (v & 0xFFFF_FF00) != 0 {
368            panic!();
369        }
370        if v == 0 {
371            None
372        } else {
373            Some(Self(v))
374        }
375    }
376}
377
378pub type LiveType = std::any::TypeId;
379
380#[derive(Clone, Debug)]
381pub struct LiveTypeInfo {
382    pub live_type: LiveType,
383    pub type_name: LiveId,
384    pub module_id: LiveModuleId,
385    pub live_ignore: bool,
386    pub fields: Vec<LiveTypeField>
387}
388
389#[derive(Clone, Debug)]
390pub struct LiveTypeField {
391    pub id: LiveId,
392    pub live_type_info: LiveTypeInfo,
393    pub live_field_kind: LiveFieldKind
394}
395
396#[derive(Copy, Clone, PartialEq, Debug)]
397pub enum LiveFieldKind {
398    Calc,
399    Deref,
400    Animator,
401    Live,
402    LiveOption
403}
404
405#[derive(Copy, Clone, Debug, PartialEq)]
406pub enum LiveBinOp {
407    Or,
408    And,
409    Eq,
410    Ne,
411    Lt,
412    Le,
413    Gt,
414    Ge,
415    Add,
416    Sub,
417    Mul,
418    Div,
419}
420
421#[derive(Copy, Clone, Debug, PartialEq)]
422pub enum LiveUnOp {
423    Not,
424    Neg,
425}
426
427
428const INLINE_STRING_BUFFER_SIZE: usize = 22;
429#[derive(Clone, Debug, PartialEq)]
430pub struct InlineString {
431    length: u8,
432    buffer: [u8; INLINE_STRING_BUFFER_SIZE]
433}
434
435impl InlineString {
436    pub fn from_str(inp: &str) -> Option<Self> {
437        let bytes = inp.as_bytes();
438        if bytes.len()<INLINE_STRING_BUFFER_SIZE {
439            let mut buffer = [0u8; INLINE_STRING_BUFFER_SIZE];
440            buffer[..bytes.len()].copy_from_slice(bytes);
441            return Some(Self {length: bytes.len() as u8, buffer})
442        }
443            None
444    }
445    
446    pub fn as_str(&self) -> &str {
447        unsafe {std::str::from_utf8_unchecked(std::slice::from_raw_parts(self.buffer.as_ptr(), self.length as usize))}
448    }
449}
450
451impl LiveValue {
452    pub fn is_open(&self) -> bool {
453        match self {
454            Self::Array |
455            Self::Expr {..} |
456            Self::TupleEnum {..} |
457            Self::NamedEnum {..} |
458            Self::Object | // subnodes including this one
459            Self::Clone {..} | // subnodes including this one
460            Self::Class {..} | 
461            Self::Root {..} => true, // subnodes including this one
462            _ => false
463        }
464    }
465    
466    pub fn is_close(&self) -> bool {
467        matches!(self, Self::Close)
468    }
469    
470    pub fn is_enum(&self) -> bool {
471        matches!(self, Self::BareEnum {..} |
472            Self::TupleEnum {..} |
473            Self::NamedEnum {..})
474    }
475    
476    pub fn is_array(&self) -> bool {
477        matches!(self, Self::Array)
478    }
479    
480    pub fn is_expr(&self) -> bool {
481        matches!(self, Self::Expr {..})
482    }
483    
484    pub fn is_class(&self) -> bool {
485        matches!(self, Self::Class {..})
486    }
487    
488    pub fn is_clone(&self) -> bool {
489        matches!(self, Self::Clone {..})
490    }
491    
492    pub fn is_object(&self) -> bool {
493        matches!(self, Self::Object)
494    }
495    
496    pub fn is_dsl(&self) -> bool {
497        matches!(self, Self::DSL {..})
498    }
499    
500    pub fn set_dsl_expand_index_if_none(&mut self, index: usize) {
501        if let Self::DSL {expand_index, ..} = self {
502            if expand_index.is_none() {
503                *expand_index = Some(index as u32)
504            }
505        }
506    }
507    
508    pub fn set_expr_expand_index_if_none(&mut self, index: usize) {
509        if let Self::Expr {expand_index, ..} = self {
510            if expand_index.is_none() {
511                *expand_index = Some(index as u32)
512            }
513        }
514    }
515    
516    pub fn get_expr_expand_index(&self) -> Option<u32> {
517        match self {
518            Self::Expr {expand_index, ..} => *expand_index,
519            _ => None
520        }
521    }
522    
523    pub fn is_id(&self) -> bool {
524        matches!(self, Self::Id(_))
525    }
526    
527    pub fn is_color(&self) -> bool {
528        matches!(self, Self::Color(_))
529    }
530    
531    pub fn is_value_type(&self) -> bool {
532        matches!(self, Self::Id(_) |
533            Self::Str(_) |
534            Self::String(_) |
535            Self::InlineString {..} |
536            Self::Dependency {..} |
537            Self::Bool(_) |
538            Self::Int64(_) |
539            Self::Float64(_) |
540            Self::Float32(_) |
541            Self::Color(_) |
542            Self::Vec2(_) |
543            Self::Vec3(_) |
544            Self::Vec4(_))
545    }
546
547    pub fn is_single_node(&self) -> bool {
548        self.is_value_type() || match self {
549            Self::Id(_) |
550            Self::IdPath(_) |
551            Self::BareEnum(_) => true,
552            _ => false
553        }
554    }
555    
556    pub fn is_structy_type(&self) -> bool {
557        match self {
558            Self::Object | // subnodes including this one
559            Self::Clone {..} | // subnodes including this one
560            Self::Class {..} => true, // subnodes including this one
561            _ => false
562        }
563    }
564    
565    pub fn is_number_type(&self) -> bool {
566        matches!(self, Self::Int64(_) |
567            Self::Float32(_) |
568            Self::Float64(_))
569    }
570    
571    pub fn as_float(&self) -> Option<f64> {
572        match self {
573            Self::Float64(v) => Some(*v),
574            Self::Float32(v) => Some(*v as f64),
575            Self::Int64(v) => Some(*v as f64),
576            _ => None
577        }
578    }
579
580    pub fn as_int(&self) -> Option<i64> {
581        match self {
582            Self::Float64(v) => Some(*v as i64),
583            Self::Float32(v) => Some(*v as i64),
584            Self::Int64(v) => Some(*v),
585            _ => None
586        }
587    }    
588    pub fn as_vec2(&self) -> Option<Vec2> {
589        match self {
590            Self::Vec2(v) => Some(*v),
591            _ => None
592        }
593    }
594    pub fn as_vec3(&self) -> Option<Vec3> {
595        match self {
596            Self::Vec3(v) => Some(*v),
597            _ => None
598        }
599    }
600    
601    pub fn as_vec4(&self) -> Option<Vec4> {
602        match self {
603            Self::Vec4(v) => Some(*v),
604            Self::Color(c) => Some(Vec4::from_u32(*c)),
605            _ => None
606        }
607    }
608    
609    pub fn as_bool(&self) -> Option<bool> {
610        match self {
611            Self::Bool(v) => Some(*v),
612            _ => None
613        }
614    }
615    
616    pub fn enum_eq(&self, id_eq:&[LiveId])->LiveValue{
617        match self{
618            Self::BareEnum(id) if *id == id_eq[0]=>{
619                LiveValue::Bool(true)
620            }
621            _=>LiveValue::Bool(false)
622        }
623    }
624    
625    pub fn enum_neq(&self, id_eq:&[LiveId])->LiveValue{
626        match self{
627            Self::BareEnum(id) if *id != id_eq[0]=>{
628                LiveValue::Bool(true)
629            }
630            _=>LiveValue::Bool(false)
631        }
632    }
633    /*
634    pub fn named_class_id(&self) -> Option<Id> {
635        match self {
636            Self::Class {class} => Some(*class),
637            _ => None
638        }
639    }*/
640    
641    pub fn set_clone_name(&mut self, name: LiveId) {
642        if let Self::Clone(clone) = self {
643            *clone = name
644        }
645    }
646    
647    pub fn get_clone_name(&self) -> LiveId {
648        match self {
649            Self::Clone(clone) => *clone,
650            _ => LiveId(0)
651        }
652    }
653    
654    pub fn variant_id(&self) -> usize {
655        match self {
656            Self::None => 0,
657            Self::Str(_) => 1,
658            Self::String(_) => 2,
659            Self::InlineString {..} => 3,
660            Self::Dependency {..} => 4,
661            Self::Bool(_) => 5,
662            Self::Int64(_) => 6,
663            Self::Float64(_) => 7,
664            Self::Float32(_) => 8,
665            Self::Color(_) => 9,
666            Self::Vec2(_) => 10,
667            Self::Vec3(_) => 11,
668            Self::Vec4(_) => 12,
669            Self::Id(_) => 13,
670            Self::IdPath{..}=>14,
671            Self::ExprBinOp(_) => 15,
672            Self::ExprUnOp(_) => 16,
673            Self::ExprMember(_) => 17,
674            Self::ExprCall {..} => 18,
675            
676            Self::BareEnum {..} => 19,
677            Self::Array => 20,
678            Self::Expr {..} => 21,
679            Self::TupleEnum {..} => 22,
680            Self::NamedEnum {..} => 23,
681            Self::Object => 24,
682            Self::Clone {..} => 25,
683            Self::Class {..} => 26,
684            Self::Root{..}=>27,
685            Self::Close => 28,
686            
687            Self::DSL {..} => 29,
688            Self::Import {..} => 30,
689            //Self::Registry {..} => 30,
690        }
691    }
692}
693
694impl Deref for LiveNode {
695    type Target = LiveValue;
696    fn deref(&self) -> &Self::Target {&self.value}
697}
698
699impl DerefMut for LiveNode {
700    fn deref_mut(&mut self) -> &mut Self::Target {&mut self.value}
701}
702