Form Input Bindings

Form input elements maintain their own internal state. The `bind()` and `on()` methods provide a way to create two-way bindings between form inputs and component state.

Written By Joel

Last updated About 1 month ago


Text Inputs

Basic text input binding using the value property:

HTML

<my-component>
  <pre rq="data">{{ placeholder }}</pre>
  <input type="text" rq="text-input">
</my-component>

JavaScript

defineComponent("my-component", {
  store: {
    message: "Hello"
  },
  setup(component, props, store) {
    // Setup two-way bindings
    component.query("text-input")
      .bind("value", () => store.message)
      .on("input", (evt) => {
        store.message = evt.target.value;
      });

    // Display store for debugging
    component.query("data").text(() => {
      return {...store};
    });
  }
})

Checkboxes

Checkbox binding using the checked property:

HTML

<my-component>
  <pre rq="data">{{ placeholder }}</pre>
  <input type="checkbox" rq="checkbox">
</my-component>

JavaScript

defineComponent("my-component", {
  store: {
    checked: false
  },
  setup(component, props, store) {
    // Setup two-way bindings
    component.query("checkbox")
      .bind("checked", () => store.checked)
      .on("change", (evt) => {
        store.checked = evt.target.checked;
      });

    // Display store for debugging
    component.query("data").text(() => {
      return {...store};
    });
  }
})

Radio Buttons

Radio button binding using the checked property:

Basic Example

Create individual radio buttons that update a single value in your store:

HTML

<my-component>
  <pre rq="data">{{ placeholder }}</pre>
  <input type="radio" rq="radio-one" name="options" value="one">
  <input type="radio" rq="radio-two" name="options" value="two">
</my-component>

JavaScript

defineComponent("my-component", {
  store: {
    selected: "one"
  },
  setup(component, props, store) {
    // Setup two-way bindings
    component.query("radio-one")
      .bind("checked", () => store.selected === "one")
      .on("change", (evt) => {
        if (evt.target.checked) store.selected = "one";
      });

    component.query("radio-two")
      .bind("checked", () => store.selected === "two")
      .on("change", (evt) => {
        if (evt.target.checked) store.selected = "two";
      });

    // Display store for debugging
    component.query("data").text(() => {
      return {...store};
    });
  }
})

Multiple Static Radio Buttons

For multiple radio buttons, you can use a loop in the setup function:

HTML

<my-component>
  <pre rq="data">{{ placeholder }}</pre>
  <input type="radio" rq="radio-one" name="options" value="one">
  <input type="radio" rq="radio-two" name="options" value="two">
  <input type="radio" rq="radio-three" name="options" value="three">
</my-component>

JavaScript

defineComponent("my-component", {
  store: {
    options: ["one", "two", "three"],
    selected: "one"
  },
  setup(component, props, store) {
    // Setup two-way bindings for each option
    store.options.forEach(value => {
      component.query(`radio-${value}`)
        .bind("checked", () => store.selected === value)
        .on("change", (evt) => {
          if (evt.target.checked) store.selected = value;
        });
    });

    // Display store for debugging
    component.query("data").text(() => {
      return {...store};
    });
  }
})

Dynamic Radio Buttons

You can also use for() to dynamically create radio buttons:

HTML

<my-component>
  <pre rq="data">{{ placeholder }}</pre>
  <input type="radio" rq="radio" name="options">
</my-component>

JavaScript

defineComponent("my-component", {
  store: {
    options: ["one", "two", "three"],
    selected: "one"
  },
  setup(component, props, store) {
    // Generate radio inputs
    component.query("radio").for(
      () => store.options,
      (el, value) => {
        // Setup two-way bindings
        el.bind("value", () => value)
          .bind("checked", () => store.selected === value)
          .on("change", (evt) => {
            if (evt.target.checked) store.selected = value;
          });
      }
    );

    // Display store for debugging
    component.query("data").text(() => {
      return {...store};
    });
  }
})

Select Elements

Select element binding using the value property:

Basic Usage

Bind a select element to track the selected option:

HTML

<my-component>
  <pre rq="data">{{ placeholder }}</pre>
  <select rq="select">
    <option value="A">Option A</option>
    <option value="B">Option B</option>
    <option value="C">Option C</option>
  </select>
</my-component>

JavaScript

defineComponent("my-component", {
  store: {
    selected: "A"
  },
  setup(component, props, store) {
    // Setup two-way bindings
    component.query("select")
      .bind("value", () => store.selected)
      .on("change", (evt) => {
        store.selected = evt.target.value;
      });

    // Display store for debugging
    component.query("data").text(() => {
      return {...store};
    });
  }
})

Dynamic Options

Use for() to create select options from an array:

HTML

<my-component>
  <pre rq="data">{{ placeholder }}</pre>
  <select rq="select">
    <option rq="option"></option>
  </select>
</my-component>

JavaScript

defineComponent("my-component", {
  store: {
    options: [
      { value: "A", text: "Option A" },
      { value: "B", text: "Option B" },
      { value: "C", text: "Option C" }
    ],
    selected: "A"
  },
  setup(component, props, store) {
    // Setup two-way bindings
    component.query("select")
      .bind("value", () => store.selected)
      .on("change", (evt) => {
        store.selected = evt.target.value;
      });

    // Generate options
    component.query("option").for(
      () => store.options,
      (el, option) => {
        el.bind("value", () => option.value)
          .text(() => option.text);
      }
    );

    // Display store for debugging
    component.query("data").text(() => {
      return {...store};
    });
  }
})

Could not load article.

Could not load article.