表单

当你在制作后台管理系统时,就会接触到很多表单输入选项。Gyron.js 的表单数据绑定和默认表单数据提交是不同的行为。

在 HTML 表单中,提交数据由 DOM 元素属性和值提供。在 Gyron.js 中,需要自定义数据的绑定以更灵活地掌控自己的数据变化。

基本例子

我们用两种不同用法对比他们的优缺点。

<form>
  <label>
    名字:
    <input type="text" name="name" />
  </label>
  <input type="submit" value="提交" />
</form>

这种写法的优点是简洁明了,用户只需在表单中输入完成后点击提交按钮即可。然而,它的缺点在于我们无法方便地修改用户输入的值。针对这个问题,Gyron.js 提供了自定义数据绑定的方法,以便更好地掌控数据变化。在使用 Gyron.js 的表单数据绑定时,我们需要自己处理数据的绑定操作,但这样能够更灵活地控制数据的变化。

import { useReactive, FC } from 'gyron'

const Form = FC(() => {
  const state = useReactive({
    name: '',
  })

  const handleSubmit = (e) => {
// 自定义提交行为
e.preventDefault() } return ( <form onSubmit={handleSubmit}> <label> 名字: <input type="text" name="name" value={state.name} onChange={(e) => (state.name = e.target.value)} /> </label> <input type="submit" value="提交" /> </form> ) })

受控组件

还需要注意的就是某些控件的值不是 value,比如<input type="checkbox" checked />的 value 就是 checked,在绑定值的时候请使用 checked。

有一个特殊的例子就是select标签,它的 value 是根据 option 的 checked 的状态来决定的,这在我们内部做了兼容处理,所以只需要关心 value 的值即可。

import { useValue, FC } from 'gyron'

const App = FC(() => {
  const selected = useValue(['bar'])

  const handleChange = (e) => {
    const value = Array.from(e.target.selectedOptions).map(
      (select) => select.value
    )
    selected.value = value
  }

  return (
    <select multiple={true} value={selected.value} onChange={handleChange}>
      <option value="foo">foo</option>
      <option value="bar">bar</option>
    </select>
  )
})

上面的例子就是一个简单的多选例子,在发生变更的时候通过 selectedOptions 来更新绑定的值,如果绑定的值发生变更也会更新 select 的状态。

如果你想管理输入状态或者需要组合输入的状态管理可以使用 onInput 或者使用onCompositionstart/onCompositionend事件。

注意:如果依赖的值没有发生变更,可以使用 update 进行更新操作

import { useValue, FC } from 'gyron'

const App = FC(({ component }) => {
  const code = useValue('')

  const handleInput = (e) => {
    code.value = e.target.value.toLocaleUpperCase()
component.update()
} return <input value={code.value} onInput={handleInput} /> })

Input

input 控件的事件和浏览器内置的事件在有些情况下表现不一样,这样做是为了兼容输入类型的控件在事件上行为保持一致。

input 控件的 change 事件在行为上和其它控件一样,在内容发生变更后立马调用,这一点和浏览器不一样,浏览器是在输入变更后焦点离开才会触发 change 事件。

import { FC } from 'gyron'

const App = FC(() => {
  function handleInput() {}
  return (
    <div>
      <input onChange={handleInput} />
      {/* 行为一致 */}
      <input onInput={handleInput} />
    </div>
  )
})