The function takes a reference to the `PathLayoutData` struct, which in
turn had a reference to the path data. The old rust generator had
special knowledge of calling solve_path_layout, so it knew to take a
reference of the path data.
In the llr there's no expression to take a reference. However since
PathData is cheap to move/copy (just holds SharedVector), we can pass it
by value (move) in the PathLayoutData.
This also means a copy in C++, which I *think* is safe, because the
constructor and destructor will be called on the C++ side, and the Rust
side still just operates on references or would try to move out a field
from the struct.
* Move the C++ elements back into private_api (despite being generated), so that struct_name_to_tokens can generate the right name in re_exports
* When generating the llr_Expression::Struct for the path elements, make sure
that all fields are filled out, to avoid an empty value expression in Expression::Struct
in the Rust generator. Since we don't generate tuples but a named struct, we must provide all fields.
This patch takes care of the lowering of events/coordinates arrays as
path data, which originates from a `commands: ...` string of SVG path
commands.
In order to minimize the path specific code in the generator, the
compile_paths now generates a Vec<Expression> for the events and
coordinates.
A `Path` with `MoveTo`/`LineTo`/etc. sub-elements now maps to an Expression::PathData of type
Type::PathData.
The llr lowering creates an Array of Type::PathElement, which is casted to PathData.
This only covers the element case. The compiled path events are still todo.
The indexes stored in `VisitChildrenResult` are unsigned. We have 64
bits to store two values and we need to have one special value as a flag.
So accept any index `< u32::MAX` instead of `< i32::MAX`, which should
allow for more data to be visited;-)
For the MCU port, we need to proccess the image to save them in the binary
in a convenient format.
This patch start this work by trying to anaylyze what format should an image
be using, and saving it as a texture in the binary.
The current graphical backend and the C++ frontend are not yet supported
This will allow later to be able to operate on the binding despite the
element is borrowed.
Since the Binding itself is in a RefCell, the analysis don't need to
be anymore.
To do this change, a small change in the binding_analysis logic was required
which means that we will now detect binding loop if a binding was causing
two binding loop. (before, only one binding loop was detected)
Somehow the focus_change_subcompo test missed this case and the visible
issue of this off-by-one was that
the combo boxes in the printer demo's settings page opened at the wrong location (wrong parent).
Pass the sub-component as a parameter in enter_component(), as it's needed in the C++
implementation, it's readily available (no need to unwrap again) and Rust will need it, too.
In the tree builder's enter_component we registered the sub-component as a member
and also registered the member initializer
in the constructor.
However the call to `init()` to initialize the bindings was registered in `enter_component_children` for no good reason.
It's cleaner to do that all in one place.
For the following reduced test-case the order in how the dynamic nodes
in the item tree were generated (and dyn indices assigned) differed from
the way the visit_dynamic_children slots were generated:
```
Blah := Rectangle {
for x in 1: Text {
text: "Should be on the right";
}
}
MainWindow := Window {
width: 772px;
height: 504px;
Text {
if (false): TouchArea {
}
}
Blah {
x: 200px;
}
}
```
The item tree node was constructed using build_item_tree, which
basically assigned dyn index 0 to the "repater" for the touch area
and "1" to the one for the repeater inside the sub-component.
Afterwards we traversed the element tree - without descending into the
sub-components - to generate the fields and the dispatch in in the
dynamic visitor. Here a subtle order would result in a mismatch of
indices:
recurse_elem_level_order would end up visiting Text, Blah and then
Text's children, assigning the first dynamic index to Blah.
This is now fixed by merging the two iterations into one.
Some code like this was generated:
`if (*self->checkbox_31.get_checked()).get()`
the remove_parentheses function removed a parentheses that it shouldn't have removed