阿里云主机折上折
  • 微信号
您当前的位置:网站首页 > 表单组件(input、checkbox、picker 等)

表单组件(input、checkbox、picker 等)

作者:陈川 阅读数:13150人阅读 分类: uni-app

uni-app 提供了丰富的表单组件,用于构建用户交互界面。这些组件包括 input、checkbox、picker 等,能够满足不同场景下的数据收集需求。下面详细介绍这些组件的使用方法和常见场景。

input 组件

input 是最基础的表单组件之一,用于接收用户输入的文本内容。uni-app 中的 input 组件支持多种类型,包括 text、number、password 等。

<template>
  <view>
    <input type="text" v-model="username" placeholder="请输入用户名" />
    <input type="password" v-model="password" placeholder="请输入密码" />
    <input type="number" v-model="age" placeholder="请输入年龄" />
  </view>
</template>

<script>
export default {
  data() {
    return {
      username: '',
      password: '',
      age: ''
    }
  }
}
</script>

input 组件支持以下常用属性:

  • type:输入类型,如 text、number、password 等
  • v-model:双向绑定数据
  • placeholder:输入框提示文字
  • maxlength:最大输入长度
  • disabled:是否禁用

checkbox 组件

checkbox 用于多选场景,可以单独使用或组合使用。uni-app 提供了两种 checkbox 使用方式:单独 checkbox 和 checkbox-group。

<template>
  <view>
    <!-- 单独使用 -->
    <checkbox v-model="checked" /> 同意协议
    
    <!-- 组合使用 -->
    <checkbox-group @change="handleChange">
      <label>
        <checkbox value="apple" /> 苹果
      </label>
      <label>
        <checkbox value="banana" /> 香蕉
      </label>
      <label>
        <checkbox value="orange" /> 橙子
      </label>
    </checkbox-group>
  </view>
</template>

<script>
export default {
  data() {
    return {
      checked: false,
      fruits: []
    }
  },
  methods: {
    handleChange(e) {
      this.fruits = e.detail.value
    }
  }
}
</script>

checkbox 组件的重要属性:

  • value:选中时的值
  • checked:是否选中
  • disabled:是否禁用
  • color:选中状态的颜色

picker 组件

picker 是选择器组件,支持多种模式:普通选择器、时间选择器、日期选择器、地区选择器等。

<template>
  <view>
    <!-- 普通选择器 -->
    <picker mode="selector" :range="options" @change="handlePickerChange">
      <view>当前选择:{{selectedOption}}</view>
    </picker>
    
    <!-- 日期选择器 -->
    <picker mode="date" :value="date" start="2020-01-01" end="2025-12-31" @change="handleDateChange">
      <view>选择日期:{{date}}</view>
    </picker>
  </view>
</template>

<script>
export default {
  data() {
    return {
      options: ['选项1', '选项2', '选项3'],
      selectedOption: '',
      date: '2023-01-01'
    }
  },
  methods: {
    handlePickerChange(e) {
      this.selectedOption = this.options[e.detail.value]
    },
    handleDateChange(e) {
      this.date = e.detail.value
    }
  }
}
</script>

picker 的不同模式:

  • selector:普通选择器
  • multiSelector:多列选择器
  • time:时间选择器
  • date:日期选择器
  • region:地区选择器

radio 组件

radio 用于单选场景,通常需要配合 radio-group 使用。

<template>
  <view>
    <radio-group @change="handleRadioChange">
      <label>
        <radio value="male" /> 男
      </label>
      <label>
        <radio value="female" /> 女
      </label>
    </radio-group>
    <view>当前选择:{{gender}}</view>
  </view>
</template>

<script>
export default {
  data() {
    return {
      gender: ''
    }
  },
  methods: {
    handleRadioChange(e) {
      this.gender = e.detail.value
    }
  }
}
</script>

radio 组件的重要属性:

  • value:选中时的值
  • checked:是否选中
  • disabled:是否禁用
  • color:选中状态的颜色

switch 组件

switch 是滑动开关组件,用于表示两种状态的切换。

<template>
  <view>
    <switch :checked="isChecked" @change="handleSwitchChange" />
    <view>当前状态:{{isChecked ? '开启' : '关闭'}}</view>
  </view>
</template>

<script>
export default {
  data() {
    return {
      isChecked: false
    }
  },
  methods: {
    handleSwitchChange(e) {
      this.isChecked = e.detail.value
    }
  }
}
</script>

switch 组件的重要属性:

  • checked:是否选中
  • disabled:是否禁用
  • color:开关的颜色
  • type:样式类型,有效值为 switch 或 checkbox

textarea 组件

textarea 是多行文本输入组件,适合需要输入大量文本的场景。

<template>
  <view>
    <textarea v-model="content" placeholder="请输入内容" auto-height />
    <view>已输入:{{content.length}}字</view>
  </view>
</template>

<script>
export default {
  data() {
    return {
      content: ''
    }
  }
}
</script>

textarea 组件的重要属性:

  • v-model:双向绑定数据
  • placeholder:输入框提示文字
  • auto-height:是否自动增高
  • maxlength:最大输入长度
  • disabled:是否禁用

slider 组件

slider 是滑动选择器组件,用于在一个范围内选择数值。

<template>
  <view>
    <slider :value="sliderValue" min="0" max="100" @change="handleSliderChange" />
    <view>当前值:{{sliderValue}}</view>
  </view>
</template>

<script>
export default {
  data() {
    return {
      sliderValue: 50
    }
  },
  methods: {
    handleSliderChange(e) {
      this.sliderValue = e.detail.value
    }
  }
}
</script>

slider 组件的重要属性:

  • value:当前值
  • min:最小值
  • max:最大值
  • step:步长
  • disabled:是否禁用
  • show-value:是否显示当前值

form 组件

form 组件用于将多个表单组件组合在一起,统一提交表单数据。

<template>
  <view>
    <form @submit="handleSubmit">
      <view class="form-item">
        <text>用户名:</text>
        <input name="username" v-model="formData.username" />
      </view>
      <view class="form-item">
        <text>密码:</text>
        <input name="password" type="password" v-model="formData.password" />
      </view>
      <button form-type="submit">提交</button>
    </form>
  </view>
</template>

<script>
export default {
  data() {
    return {
      formData: {
        username: '',
        password: ''
      }
    }
  },
  methods: {
    handleSubmit(e) {
      console.log('表单数据:', this.formData)
      uni.showToast({
        title: '提交成功',
        icon: 'success'
      })
    }
  }
}
</script>

<style>
.form-item {
  margin-bottom: 20rpx;
  display: flex;
  align-items: center;
}
</style>

form 组件的重要属性:

  • report-submit:是否返回 formId,用于发送模板消息
  • @submit:提交表单时触发的事件
  • @reset:重置表单时触发的事件

表单验证

在实际开发中,表单验证是必不可少的环节。uni-app 可以通过多种方式实现表单验证。

<template>
  <view>
    <form @submit="handleSubmit">
      <view class="form-item">
        <text>用户名:</text>
        <input name="username" v-model="formData.username" />
        <text v-if="errors.username" class="error">{{errors.username}}</text>
      </view>
      <view class="form-item">
        <text>密码:</text>
        <input name="password" type="password" v-model="formData.password" />
        <text v-if="errors.password" class="error">{{errors.password}}</text>
      </view>
      <button form-type="submit">提交</button>
    </form>
  </view>
</template>

<script>
export default {
  data() {
    return {
      formData: {
        username: '',
        password: ''
      },
      errors: {
        username: '',
        password: ''
      }
    }
  },
  methods: {
    validateForm() {
      let isValid = true
      
      if (!this.formData.username) {
        this.errors.username = '用户名不能为空'
        isValid = false
      } else {
        this.errors.username = ''
      }
      
      if (!this.formData.password) {
        this.errors.password = '密码不能为空'
        isValid = false
      } else if (this.formData.password.length < 6) {
        this.errors.password = '密码长度不能少于6位'
        isValid = false
      } else {
        this.errors.password = ''
      }
      
      return isValid
    },
    handleSubmit(e) {
      if (this.validateForm()) {
        console.log('表单验证通过,提交数据:', this.formData)
        uni.showToast({
          title: '提交成功',
          icon: 'success'
        })
      }
    }
  }
}
</script>

<style>
.error {
  color: red;
  font-size: 12px;
  margin-left: 10px;
}
.form-item {
  margin-bottom: 20rpx;
  display: flex;
  align-items: center;
}
</style>

自定义表单组件

在实际项目中,可能需要封装一些自定义的表单组件。下面是一个自定义评分组件的示例。

<template>
  <view>
    <view class="rating-container">
      <text v-for="i in 5" :key="i" @click="handleRate(i)" 
            :class="['iconfont', i <= rating ? 'icon-star-fill' : 'icon-star']">
      </text>
    </view>
    <input type="hidden" name="rating" :value="rating" />
  </view>
</template>

<script>
export default {
  data() {
    return {
      rating: 0
    }
  },
  methods: {
    handleRate(value) {
      this.rating = value
    }
  }
}
</script>

<style>
.rating-container {
  display: flex;
}
.iconfont {
  font-size: 24px;
  margin-right: 5px;
}
.icon-star-fill {
  color: #f5a623;
}
.icon-star {
  color: #ccc;
}
</style>

表单数据绑定

uni-app 提供了多种数据绑定方式,最常用的是 v-model 双向绑定。

<template>
  <view>
    <input v-model="message" placeholder="请输入内容" />
    <view>输入的内容:{{message}}</view>
    
    <!-- 自定义组件使用 v-model -->
    <custom-input v-model="customValue" />
    <view>自定义组件的值:{{customValue}}</view>
  </view>
</template>

<script>
export default {
  data() {
    return {
      message: '',
      customValue: ''
    }
  }
}
</script>

对于自定义组件,要实现 v-model 需要定义 model 选项:

// 自定义组件内部
export default {
  model: {
    prop: 'value',
    event: 'input'
  },
  props: {
    value: {
      type: String,
      default: ''
    }
  },
  methods: {
    handleInput(e) {
      this.$emit('input', e.target.value)
    }
  }
}

表单提交与重置

form 组件支持提交和重置操作,可以通过 form-type 属性指定按钮类型。

<template>
  <view>
    <form @submit="handleSubmit" @reset="handleReset">
      <input name="username" v-model="formData.username" placeholder="用户名" />
      <input name="password" type="password" v-model="formData.password" placeholder="密码" />
      
      <button form-type="submit">提交</button>
      <button form-type="reset">重置</button>
    </form>
  </view>
</template>

<script>
export default {
  data() {
    return {
      formData: {
        username: '',
        password: ''
      }
    }
  },
  methods: {
    handleSubmit(e) {
      console.log('提交数据:', this.formData)
    },
    handleReset() {
      this.formData = {
        username: '',
        password: ''
      }
    }
  }
}
</script>

表单组件样式定制

uni-app 中的表单组件可以通过 CSS 进行样式定制。

<template>
  <view>
    <input class="custom-input" placeholder="自定义样式输入框" />
    <button class="custom-button">自定义按钮</button>
  </view>
</template>

<style>
.custom-input {
  border: 1px solid #ddd;
  border-radius: 4px;
  padding: 10px;
  margin: 10px 0;
}

.custom-button {
  background-color: #4CAF50;
  color: white;
  border: none;
  padding: 10px 20px;
  border-radius: 4px;
  margin-top: 10px;
}

.custom-button:active {
  background-color: #3e8e41;
}
</style>

表单组件性能优化

当表单比较复杂时,需要注意性能优化:

  1. 避免在模板中使用复杂表达式
  2. 对大表单进行分步加载
  3. 使用 v-if 和 v-show 合理控制组件显示
  4. 对频繁变化的数据使用防抖或节流
<template>
  <view>
    <!-- 使用 v-show 替代 v-if 保持组件状态 -->
    <view v-show="showSection1">
      <!-- 表单内容 -->
    </view>
    
    <!-- 使用防抖处理输入 -->
    <input v-model="searchText" @input="debounceSearch" />
  </view>
</template>

<script>
export default {
  data() {
    return {
      searchText: '',
      debounceTimer: null,
      showSection1: true
    }
  },
  methods: {
    debounceSearch() {
      clearTimeout(this.debounceTimer)
      this.debounceTimer = setTimeout(() => {
        this.doSearch()
      }, 500)
    },
    doSearch() {
      // 实际搜索逻辑
    }
  }
}
</script>

表单组件与后端交互

表单数据通常需要提交到后端服务器,可以使用 uni.request 方法。

<template>
  <view>
    <form @submit="handleSubmit">
      <input name="username" v-model="formData.username" />
      <input name="password" type="password" v-model="formData.password" />
      <button form-type="submit">登录</button>
    </form>
  </view>
</template>

<script>
export default {
  data() {
    return {
      formData: {
        username: '',
        password: ''
      }
    }
  },
  methods: {
    handleSubmit() {
      uni.request({
        url: 'https://api.example.com/login',
        method: 'POST',
        data: this.formData,
        success: (res) => {
          if (res.data.success) {
            uni.showToast({ title: '登录成功' })
          } else {
            uni.showToast({ title: res.data.message, icon: 'none' })
          }
        },
        fail: (err) => {
          uni.showToast({ title: '网络错误', icon: 'none' })
        }
      })
    }
  }
}
</script>

表单数据持久化

可以使用 uni.setStorage 将表单数据临时保存到本地。

<template>
  <view>
    <input v-model="draft.title" placeholder="标题" />
    <textarea v-model="draft.content" placeholder="内容"></textarea>
    <button @click="saveDraft">保存草稿</button>
    <button @click="loadDraft">加载草稿</button>
  </view>
</template>

<script>
export default {
  data() {
    return {
      draft: {
        title: '',
        content: ''
      }
    }
  },
  methods: {
    saveDraft() {
      uni.setStorage({
        key: 'formDraft',
        data: this.draft,
        success: () => {
          uni.showToast({ title: '草稿保存成功' })
        }
      })
    },
    loadDraft() {
      uni.getStorage({
        key: 'formDraft',
        success: (res) => {
          this.draft = res.data
          uni.showToast({ title: '草稿加载成功' })
        }
      })
    }
  }
}
</script>

表单组件国际化

对于多语言应用,表单组件需要支持国际化。

<template>
  <view>
    <input :placeholder="$t('form.username')" v-model="username" />
    <input :placeholder="$t('form.password')" type="password" v-model="password" />
  </view>
</template>

<script>
export default {
  data() {
    return {
      username: '',
      password: ''
    }
  }
}
</script>

// 语言资源文件
// en.json
{
  "form": {
    "username": "Username",
    "password": "Password"
  }
}

// zh-CN.json
{
  "form": {
    "username": "用户名",
    "password": "密码"
  }
}

表单组件无障碍访问

为了提高可访问性,表单组件应该添加适当的 ARIA 属性。

<template>
  <view>
    <label for="username">用户名:</label>
    <input id="username" aria-label="用户名输入框" v-model="username" />
    
    <label for="password">

本站部分内容来自互联网,一切版权均归源网站或源作者所有。

如果侵犯了你的权益请来信告知我们删除。邮箱:cc@cccx.cn

前端川

前端川,陈川的代码茶馆🍵,专治各种不服的Bug退散符💻,日常贩卖秃头警告级的开发心得🛠️,附赠一行代码笑十年的摸鱼宝典🐟,偶尔掉落咖啡杯里泡开的像素级浪漫☕。‌