Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Scoped slots API #8

Open
edimitchel opened this issue Oct 31, 2020 · 5 comments
Open

Scoped slots API #8

edimitchel opened this issue Oct 31, 2020 · 5 comments

Comments

@edimitchel
Copy link

Web Components with slots permit to provide more reusable components and to write less props for more features.

BUT,
when we want some contextual data, we are lost and we have to create slots depending to initial data..

Vue introduces Scoped Slots which adds the possibility to build slot using contextual props, aka Scoped props.

See more : https://vuejs.org/v2/guide/components-slots.html#Scoped-Slots

It's possible to improve that on Web Components ?

@edimitchel edimitchel changed the title Scope slots Scope slotsd Oct 31, 2020
@edimitchel edimitchel changed the title Scope slotsd Scoped slots API Oct 31, 2020
@web-padawan
Copy link

I'm hesitant about implementing this as a protocol. Vue.js scoped slots are a framework-specific concept (please don't be confused by its usage of <slot> in the template syntax) that mixes two things: DOM composition and data flow.

Standard based <slot> elements are only about DOM composition. Passing data to slotted components could be done using slotchange event. But in general it's up to library authors to decide how to handle the data flow on their side.

@Westbrook
Copy link
Collaborator

This certainly is an interesting API, though I do worry that @web-padawan is right about it needing to be framework specific. @edimitchel can you think of a starting place from which you’d want to see something like this made possible cross renderer?

There seems like the possibility of a sort of three sides context API pattern here, content element messages to its parent to establish content and the parent messages the wrapping element with context to trigger updates, maybe... However, structuring that in a way that made sense in a number of different renders sound like quite the task.

@EisenbergEffect
Copy link

This is a scenario that I've managed quite elegantly with dependency injection for a good 15+ years on projects of all sizes. I've also built DI on top of React's context API successfully, used by a large-scale React app (>1MM LoC). I need to review the context API proposal here, but if it's similar in concept to React's then I don't foresee it being a problem to handle these scenarios without introducing an additional concept around slots. I think it's likely that a basic context api could handle this scenario, and a layered DI could provide app-specific power above it if needed, without the need to mix the concerns of UI composition with data/service location.

@justinfagnani
Copy link
Member

I think there are two things we could reasonably do as community protocols in this space:

  1. Define a rendering-library agnostic "render props" callback API. Render callbacks are pretty trivial to do with many libraries, lit-html say, but it's a bit trickier if you want to let a render prop callback use any rendering library.

    One way to do this generically is to define a callback signature like renderCallback(data, container). Render callbacks would then contain their own call to their template library of choice. Components would be responsible for providing the callback with a container to render to and timing the callback correctly.

    See [lit-html] Consider adding a render-prop directive lit/lit#1478 for a write up on how we might expose this in Lit.

  2. Create a "template processor" protocol so that <template> tags can be used as render props. This would be inspired by the template processor concept from the first Template Instantiation proposal. A template processor would be registered so it could be referenced by name in an attribute, and would probably be a function that given a template returns a render callback as specified in (1).

    With that you could do:

    <my-list>
      <template processor="my-processor">
         <h1>Hello {{name}}</h1>
      </template>
    </my-list>

@Westbrook
Copy link
Collaborator

@edimitchel I wonder how you see this aligning with the discussion in #45?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

5 participants