Git Product home page Git Product logo

Comments (5)

rylev avatar rylev commented on July 23, 2024

The LayoutCtx also has reference to a WindowState which is highly Windows specific. This will need to be abstracted, but I think we can leave that for phase 2.

from druid.

raphlinus avatar raphlinus commented on July 23, 2024

These are great questions. Here's my thinking, though I'm very flexible if better solutions pop up.

Signature of paint

The current design of PaintCtx has been creating lots of problems and needs to be reworked. One problem is that the use of a getter function to get the rendering context causes borrowing problems, described in very good detail in a blog post by Niko Matsakis. Of the solutions presented there, I've been leaning toward the "view struct", which would basically have a &mut piet::RenderContext as a field in PaintCtx. It would also be possible to have RenderContext as an additional field (ie the "Free variables" approach) but I don't see a significant advantage. The extra information ("hot" and so on) will continue to grow.

At some point soon, we'll have to address this question again, as we'll need a more robust mechanism for resources in general, and also to pass theme information into widgets. But we shouldn't block the platform independent drawing on that.

Thus, my recommendation for the signature of paint: keep it basically the same as now, but access the piet RenderContext as a field rather than through a getter function.

Context for text layout

Right. In terms of the architectural goals, no. But we do need a "factory" that can be used to make text layouts, at the very least. RenderContext is an abstraction of a surface that can be painted on. I'll note that Android makes this distinction fairly cleanly - an Android Canvas is very similar to piet RenderContext, and they also have a Paint, which has the dual functions of a Brush and a factory-ish object for text layout.

In practice, in the current code we do always have a RenderContext when we do layout, but as I say I don't want to bake in that assumption. Among other things, I don't want to preclude multi-threaded layout.

The solution is to have a trait that specifically acts as a text factory, but is not bound to drawing on a particular surface. In order to avoid too much bureaucracy, it might be good to have RenderContext deref to it. I'll see if I can prototype something up.

While it's on my mind, another note: the "resources and theme info" mentioned above for painting also needs to be plumbed in to layout.

LayoutCtx

This is probably confusing naming, as for ownership reasons LayoutCtx basically owns all the UI state that's not per-widget state. The WindowState struct will no doubt be abstracted by druid-shell, and probably be governed by a trait. I think it makes sense to tackle widget drawing first before getting into that.

from druid.

rylev avatar rylev commented on July 23, 2024

@raphlinus So i tried changing PaintCtx and ran into several issues:

  • If you make PaintCtx take a &mut piet::RenderContext than you must specify concrete types for the associated types. I've found some work-arounds for boxing traits without having to specify associated types (in short, avoid the problem completely by creating new traits that don't specify associated types: https://users.rust-lang.org/t/trait-objects-with-associated-types/746), but this does not work for our case.
  • The next option is to do PaintCtx<T: piet::RenderContext>. The issue now is that this requires the paint function on Widget to be generic over the same T: piet::RenderContext. Once this happens, Widget is no longer object safe. This means we can't have Vec<Widget> anymore which breaks a whole bunch of other code.

This is pushing my knowledge of Rust's type system pretty far. I could not come up with a solution to fix this unfortunately. The only thing I can think of trying is doing some cfg magic, but I didn't want to go down that route if I'm missing something obvious. Any ideas?

from druid.

raphlinus avatar raphlinus commented on July 23, 2024

Ah, we have indeed run smack into the limits of the Rust type system. My sense is that we should concretize the RenderContext type at the druid level, which is probably similar to the last thing you said. I don't think you're missing something obvious, but this is probably something we should think about more.

Thanks again for digging into this, it's probably deeper water than either of us expected.

from druid.

raphlinus avatar raphlinus commented on July 23, 2024

I'm going to think about this some more, but will throw out one idea: a way to achieve loose coupling in Rust is Any. I have already been thinking about that as an "escape hatch" so that it's possible to access platform-specific features, but it could also be the way a RenderContext accesses it associated resources such as brushes and text layouts. It would be a loss of static type checking (creating a text layout in Cairo and passing it to Direct2D would be possible and thus a runtime error), but certainly more flexible than concretizing and thus possibly a better solution.

from druid.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.