/// import { computed, Default, NAME, pattern, UI } from "commontools"; import { decrement, increment, nth, previous } from "../counter-handlers.ts"; interface RecipeState { value: Default; } export const Counter = pattern((state) => { return { // computed() is used to create reactive derived values [NAME]: computed(() => `Simple counter: ${state.value}`), [UI]: (
{ /* Even though we could end up passing extra data to decrement, our schema prevents that actually reaching the handler. In fact, we are passing `value` as an OpaqueRef here but it becomes a Cell at invocation time */ } dec to {previous(state.value)} {/* transforms pure functions (like nth) into the `derive(c, nth)` equivalent */} Counter is the {nth(state.value)} number inc to {state.value + 1}
), value: state.value, }; }); /* This demonstrates a pattern of passing a Cell to a sub-pattern and keeping the value in sync between all locations. It also demonstrates that any pattern can be invoked using JSX syntax. */ export default pattern((state) => { // A pattern can be 'invoked' directly const counter = Counter({ value: state.value }); return { [NAME]: computed(() => `Double counter: ${state.value}`), [UI]: (
{/* Patterns can also be 'invoked' via JSX*/} {/* These methods of rendering are functionally equivalent, you may prefer the explicit case for non-UI patterns */} {counter}
), value: state.value, }; });