proposal-signals
proposal-signals copied to clipboard
Should some EventTargets also be Signals?
Some DOM event targets (such as MediaQueryList, returned by matchMedia as well as AbortSignal) have a single property and a single event that emits whenever that property's value changes. While signals could be offered as a second property, it might also be nice to have some way for a class to inherit both EventTarget and Signal.
const mql = window.matchMedia('(max-width: 900px)');
const isSmallScreen = new Signal.Computed(() => mql.get());
I'm also really happy to see Signal.subtle.watched/Signal.subtle.unwatched which makes it pretty easy to wrap these APIs in userland :) It's missing from a lot of framework Signal libraries.
function matchMediaSignal(query) {
const mql = window.matchMedia(query);
const abortController = new AbortController();
const signal = new Signal.State(mql.matches, {
[Signal.subtle.watched]() {
this.set(mql.matches);
mql.addEventListener('change', () => this.set(mql.matches), { signal: abortController.signal });
},
[Signal.subtle.unwatched]() {
abortController.abort();
}
});
}
similiar issue: https://github.com/proposal-signals/proposal-signals/issues/88 Thank you for adding a use case.
This is an excellent question and corresponds much more closely to how I would like to see signals integrate with the web platform than #88. @wycats was telling me about an idea for ResizeObserver to integrate with signals in a similar way. Let’s develop more examples of how this integration should look—it is nice to see that the signal versions of web APIs can be built as a library on top, as demonstrated above.
For what it's worth, I think the critical question is not whether the EventEmitter emits an event with a single value when the value changes, but rather whether it's safe to ignore intermediate values until you're ready to use them in another computation.
(In my opinion, if a lossless stream of intermediate values are important, Observables are a much more effective abstraction).
That said, I think it is quite common for Signal-like modelling to make sense for situations that currently use EventEmitter and I think it's a wide open design space for exploration.
Broadly speaking, I think the *Observer DOM APIs are the strongest initial candidates, because those APIs are already intended to be used in discrete ways (and intentionally batch up changes until a particular phase in the rendering pipeline).