starbeamjs / starbeam

Fun and simple reactivity
Other
343 stars 16 forks source link

Web Component Renderer and General Renderer Guidance #124

Open EisenbergEffect opened 1 year ago

EisenbergEffect commented 1 year ago

I'm working on a Web Components course, and I'd like to add a lesson on Starbeam, showing how to integrate it with a Web Component. Looking through the documentation, it's very clear how to use Starbeam for creating reactive models (great job!) but not so clear on how to build the library/framework integrations. Can anyone provide me some guidance on this?

My situation is pretty simple, I just want a basic DOM integration. For example, here's what I do with Reactively to demonstrate that:

const template = html`
  <button id="decrement">-</button>
  <span id="value"></span>
  <button id="increment">+</button>
`;

class MyCounter extends WebComponent {
  #counter = reactive(0); // this would be replaced by a Starbeam Cell

  constructor() {
    super();
    this.refs.decrement.addEventListener("click", () => this.#counter.value--);
    this.refs.increment.addEventListener("click", () => this.#counter.value++);
    // How best do I do this? Do I need to use a Resource?
    reactive(() => this.refs.value.innerText = this.#counter.value, { effect: true }); 
  }
}

// Below tells Reactively's effect system to start scheduling effect updates.
// How would I do this with Starbeam?
autoStabilize(); 

Is there an easy way to trigger batch renders using a micro task queue or rAF, for example?

NullVoxPopuli commented 1 year ago

Hello! Things are still in flight, and the vanilla renderer is due for an overhaul, but to unblock, there is the DEBUG_RENDERER, which would look like this:

    import { Cell, DEBUG_RENDERER } from "@starbeam/universal";

    let inc = document.getElementById('increment');
    let dec = document.getElementById('decrement');
    let val = document.getElementById('value');

    let value = Cell(0);

    inc.addEventListener('click', () => value.current++);
    dec.addEventListener('click', () => value.current--);

    DEBUG_RENDERER.render({
      render() {
        val.innerHTML = value.current;
      },
      debug() {}
    });

Maybe @wycats knows of a better way to do this for little demos like this?

BenjaminBeck commented 1 year ago

Nice, thanks. I have some experience with ember and i watched a youtube video where starbeamjs got mentioned. Today i encountered a task where reactivity or computed properties would be a great help. But it is in a existing, normal website. I did not find any infos about vanilla js usage on starbeamjs.com, but luckily i found it here.