Uni-app表单校验与键盘适配实战

今天要聊的是用户和 App 交互最频繁、也最容易劝退用户的环节------表单开发(Forms & Validation)

在 Uni-app 中,原生 <form> 标签的功能非常弱。如果你还在用 if (username === '') 这种方式手动写校验逻辑,那你的代码很快就会变成"面条代码"。今天我们重点推荐官方的 uni-forms 组件,以及解决那个让所有移动端开发者头疼的**"键盘遮挡输入框"**问题。


🚀 今日份:优雅的表单校验与键盘适配

1. 核心神器:uni-forms (Schema Validation)

Uni-app 官方提供的 uni-ui 库中,uni-forms 是最强大的组件之一。它支持声明式校验,也就是说,你只需要把规则写好,剩下的交给组件。

🛠️ 实战代码:标准登录表单

html 复制代码
<template>
  <view class="container">
    <uni-forms ref="form" :modelValue="formData" :rules="rules">
      
      <uni-forms-item label="账号" name="username">
        <uni-easyinput v-model="formData.username" placeholder="请输入用户名" />
      </uni-forms-item>

      <uni-forms-item label="密码" name="password">
        <uni-easyinput type="password" v-model="formData.password" placeholder="请输入密码" />
      </uni-forms-item>

    </uni-forms>
    
    <button @click="submit">登录</button>
  </view>
</template>

<script>
export default {
  data() {
    return {
      formData: {
        username: '',
        password: ''
      },
      // 3. 校验规则配置
      rules: {
        username: {
          rules: [{
            required: true,
            errorMessage: '用户名不能为空'
          }]
        },
        password: {
          rules: [{
            required: true,
            errorMessage: '密码不能为空'
          }, {
            minLength: 6,
            errorMessage: '密码长度不能少于6位'
          }]
        }
      }
    }
  },
  methods: {
    submit() {
      // 4. 触发校验
      this.$refs.form.validate().then(res => {
        console.log('校验通过,表单数据:', res);
        // 这里发送 uni.request
      }).catch(err => {
        console.log('校验失败:', err);
      })
    }
  }
}
</script>

2. 进阶校验:自定义规则 (Custom Validator)

有时候正则表达式搞不定,比如"确认密码必须等于密码"。这时候需要自定义校验函数

javascript 复制代码
rules: {
  confirmPassword: {
    rules: [{
      required: true,
      errorMessage: '请确认密码'
    }, {
      validateFunction: (rule, value, data, callback) => {
        // value 是当前输入的值,data 是整个表单数据
        if (value !== data.password) {
          callback('两次输入的密码不一致');
        }
        return true;
      }
    }]
  }
}

3. 痛点解决:键盘遮挡输入框 (Keyboard Occlusion)

这是移动端开发最经典的 Bug:用户点击底部的输入框,软键盘弹起,直接把输入框挡住了,用户盲打。

方案 A:cursor-spacing (原生 Input 属性)

最简单,但只对原生 input 有效。

html 复制代码
<input cursor-spacing="20" />

方案 B:页面整体上推 (推荐)

pages.json 中配置 style

json 复制代码
{
  "path": "pages/login/login",
  "style": {
    "app-plus": {
      "softinputMode": "adjustResize" // 安卓推荐:自动调整窗口大小
    }
  }
}
  • adjustResize: 页面高度会被压缩,输入框自动挤上去(推荐)。
  • adjustPan: 整个页面向上平移,顶部导航栏可能会被顶出屏幕。

方案 C:手动滚动 (终极法宝)

如果上面的都失效(常见于 iOS),可以在输入框获取焦点(@focus)时,手动滚动页面:

javascript 复制代码
onFocus(e) {
  // 获取键盘高度(需要监听 keyboardHeightChange)
  // 或者简单粗暴地滚动到底部
  uni.pageScrollTo({
    scrollTop: 9999,
    duration: 100
  });
}

4. 交互优化小细节

  1. 自动聚焦 :进入页面直接弹出键盘。<input focus="true" />
  • 注意:App 端效果好,H5 iOS 端因安全限制,通常必须由用户手触触发。
  1. 键盘右下角按钮:控制是"完成"还是"下一项"。
html 复制代码
<input confirm-type="next" /> <input confirm-type="search" /> <input confirm-type="done" />   ```
配合 `@confirm` 事件使用。

💡 核心总结

  1. 拒绝手动校验 :务必使用 uni-forms,代码量减少 50%,逻辑清晰度提升 100%。
  2. 校验时机 :推荐配置 validate-trigger="bind",失焦时实时校验,体验比点提交按钮才报错要好。
  3. 键盘适配 :优先配置 pages.jsonsoftinputMode,搞不定再用 JS 手动滚动。

相关推荐
林九生3 分钟前
【Flutter】Flutter 拍照/相册选择后无法显示对话框问题解决方案
前端·javascript·flutter
程序员小寒9 分钟前
JavaScript设计模式(四):发布-订阅模式实现与应用
开发语言·前端·javascript·设计模式
Highcharts.js9 分钟前
Highcharts Gantt 实战:从框架集成到高级功能应用-打造现代化、交互式项目进度管理图表
前端·javascript·vue.js·信息可视化·免费
程序猿的程12 分钟前
把股票数据能力接进 AI:stock-sdk-mcp 的实践整理
前端·javascript·node.js
终端鹿19 分钟前
setup 语法糖从 0 到 1 实战教程
前端·javascript·vue.js
周淳APP20 分钟前
【React Fiber架构+React18知识点+浏览器原生帧流程和React阶段流程相串】
前端·javascript·react.js·架构
reasonsummer21 分钟前
【白板类-01-01】20260326水果连连看01(html+希沃白板)
前端·html
HelloReader22 分钟前
Qt Quick 视觉元素、交互与自定义组件(七)
前端
We་ct25 分钟前
LeetCode 153. 旋转排序数组找最小值:二分最优思路
前端·算法·leetcode·typescript·二分·数组
程序员阿峰27 分钟前
前端3D·Three.js一学就会系列:第二 画线
前端·three.js