3 ms·
> two panes 10px apart `gap: 10px` > put elements on top of it in the bottom left corner, bottom right corner and align margins of the content within the pane
by onsclom 3y ago
> two panes 10px apart
`gap: 10px`
> put elements on top of it in the bottom left corner, bottom right corner and align margins of the content within the pane anchoring elements manually is so much easier
These instructions seem a bit more vague. If you make this visually or with QML I'm sure I can replicate it in an intuitive way with flexbox.
Flexbox has `align-items`, `justify-content`, `align-content` which covers all the needs of aligning to centers or corners. `padding` and `margin` work exactly like you'd expect. Unlike QML's layouts, you can also enable `flex-wrap` so content automatically wraps when it overflows the allocated space.
Maybe you're also wondering, how do I memorize all these flexbox properties? I don't! Chrome dev tools give you a GUI for editing a flexbox[1], isn't that really nice?
With all these tools, hopefully it becomes clear that you never need to manually define anchors. You can compose these layouts to build whatever complex layouts your heart desires. But, if you are still really attached to the anchor workflow, you can do that with CSS as well. For example, `position: absolute; bottom: 100%; right: 100%` would anchor a child element to the bottom right of its parent.
> The beauty of QML is that I can treat RowLayout and Row as elements written in QML itself.
I totally agree here. My Svelte example from above would become:
<RowLayout>
<p>pane 1</p>
<p>pane 2</p>
</RowLayout>
What if I told you it's totally trivial to make this RowLayout component yourself in Svelte? This could totally be valid Svelte code! If this sounds interesting, this example[2] is a great starting point. And it would be even more trivial to pull in a great component library like Skeleton UI[3] which does stuff like this for you.
> If I recall accurately it is possible to loop through child elements and assign properties to them such as anchors with respect to sibiling elements. The abstraction thus is more fundamental.
Hopefully this RowLayout example makes it clear that Svelte can also loop through child elements and assign properties.
> Inheritance is the right abstraction for the UI elements
How are you so sure about this? React is one of the most popular and successful tools for building UI elements, and it avoids inheritance entirely. Do you think React's approach is totally offbase? Similarly, Rust and Go do not have inheritance at all. Do you disagree with their design?
> For instance I don’t need to predict all properties in advance for my custom bottom implemention when used in the code. Assuming that all of them are available is quite powerful and allows to experiment in place.
You can expose properties with composition based elements too! You don't need inheritance to support this workflow.
> Nevertheless, can you come up with `footguns of inheritance` to which QML is susceptible to?
I think the composition over inheritance wiki page[4] explains things much more elegantly than I ever could. Though I do think I made a mistake. Does inheritance actually exists in QML land? I don't think so.
It feels like you compose things very similarly to Svelte or React. Maybe it's a just a semantics thing, but imagine HelloText.qml:
Text {
text: "hello world!"
}
Does HelloText inherit from from "Text"? I'd say no. HelloText simply instantiates Text and sets its' text property to "hello world". Though I imagine you would say HelloText inherits from Text and overrides the text property?
Compare this to the Qt Widget world where the difference between inheritance and composition are much more clear. Sometimes a Qt Widget doesn't expose the properties or functionality you want. The best scenario is when Qt Widgets do expose the properties you need. Then you can instantiate them and change those properties. Notice that even Qt Widgets sometimes expose properties without inheritance! When defining bigger fancier widgets, why require inheritance? Break them into smaller parts and expose useful properties. Then you and other programmers can compose custom behavior without going through the sludge of inheriting and overriding!
Perhaps we already agree on that part and it was just a semantics issue about whether QML is actually using composition or inheritance?
> This sounds interesting. I will give it a try on someday when I will need to make an UI in HTML.
Yay, I'm interested to hear what you think!
[1] https://developer.chrome.com/docs/devtools/css/flexbox/ https://developer.chrome.com/docs/devtools/css/flexbox/
[2] https://svelte.dev/examples/slots https://svelte.dev/examples/slots
[3] https://www.skeleton.dev/ https://www.skeleton.dev/
[4] https://en.wikipedia.org/wiki/Composition_over_inheritance https://en.wikipedia.org/wiki/Composition_over_inheritance
- rubymamis 3y agoBTW, someone created Flexbox for QML: https://github.com/tripolskypetr/qml-flexbox https://github.com/tripolskypetr/qml-flexbox
- onsclom 3y agoIt's really awesome someone did this. If you just want the expressiveness of flexbox and don't care about performance, this is perfect! However, wouldn't the performance for this be very optimal? Check out the `Flex.qml` code[1]. It's all very unoptimized and dynamic QMLScript. None of the function arguments are typed. There is no way the QML compiler is turning any of this into efficient, statically typed C++ code. The beauty of using flexbox in the browser is that all the layout calculations are done natively in the browser without ever touching JavaScript. [1] https://github.com/tripolskypetr/qml-flexbox/blob/master/qml/Flex.qml https://github.com/tripolskypetr/qml-flexbox/blob/master/qml...
- rubymamis 3y agoNope, from what I can tell the entire backend is a Qt C++ binding[1] for the C++ Yoga library[2][3]. You can see the Qt C++ backend is exposed to QML here[4]. So it's C++ all the way down just in a comfortable setting. [1] https://github.com/tripolskypetr/qml-flexbox/blob/master/objects/flex/flexnode.h https://github.com/tripolskypetr/qml-flexbox/blob/master/obj... [2] https://github.com/tripolskypetr/qml-flexbox/tree/master/third_party/yoga https://github.com/tripolskypetr/qml-flexbox/tree/master/thi... [3] https://github.com/facebook/yoga https://github.com/facebook/yoga [4] https://github.com/tripolskypetr/qml-flexbox/blob/677a1287df8c1a5d6c35f33705be251828daf901/main.cpp#L16 https://github.com/tripolskypetr/qml-flexbox/blob/677a1287df... P.S. I'll answer your other reply very soon. I'm releasing a new version of my app so it takes its toll on me.
- onsclom 3y agoWhoops, I should have been more clear. When I said "It's all very unoptimized and dynamic QMLScript" I meant just the file `Flex.qml`. I'm sure the Qt C++ bindings are fast and great, but check out the `updatePositions` function in `Flex.qml`[1]. This unoptimized and dynamic QMLScript gets ran every time a flex item's width, height, or children change. I imagine if that QMLScript was given types then at least that QMLScript compiler could generate some C++ for it, but right now there are no types so I doubt there is any efficient C++ generated for this script. On the web it's common to animate the size of flexbox items with CSS animations. These animations are entirely implemented by the browser, and I imagine much of it is even GPU accelerated. No JavaScript is executed for this on the browser. But with this library, you would be running the `Flex.qml`'s `updatePositions` function every frame of the animation. Isn't that wasteful when compared to how flexbox works in the browser? It seems like a browser would be much faster at computing layout for flexbox elements than this, especially when that flexbox's size is being animated with CSS animations. [1] https://github.com/tripolskypetr/qml-flexbox/blob/master/qml/Flex.qml#L271 https://github.com/tripolskypetr/qml-flexbox/blob/master/qml...