javascript将异步校验表单改写为同步表单


Posted in Javascript onJanuary 27, 2015

同步表单校验的缺点

响应错误信息时,需要重新加载整个页面(虽然有缓存,客户端仍然需要通过http协议对比每个文件是否有更新,以保持文件最新)
服务器响应错误以后,用户之前所输入的信息全部丢失了,用户需要从头开始填写(部分浏览器帮我们缓存了这些数据)

异步校验表单的初衷

提升用户体验
最大化减少网络请求,减轻服务器压力
下面我们看一个常见的异步表单校验(校验工号在后台是否存在,存在为有效工号)

javascript将异步校验表单改写为同步表单

校验工号

var BASE_PATH = '${rc.contextPath}';

var $workerIdInput = $('#workerIdInput');

var $workerIdError = $('#workerIdError');

//标识用户输入的工号是否正确

var isWorkerIdCorrect = false;

var ERROR_WORKER_ID_IS_NULL = "员工工号不能为空";

var ERROR_WORKER_ID_IS_NOT_CORRECT = "请输入有效的员工工号";

//显示错误信息

function showWorkerIdError(errorMessage) {

  $workerIdError.html(errorMessage);

  $workerIdError.show();

}

//隐藏错误信息

$workerIdInput.on('keydown', function() {

  $workerIdError.hide();

});

//将上次输入的工号保存起来

$workerIdInput.on('focus', function() {

  var workerId = $.trim($(this).val());

  $(this).data('before', workerId);

});

//blur时进行校验

$workerIdInput.on('blur', function() {

  var workerId = $.trim($(this).val());

  //长度为0时,显示工号为空的错误信息

  if (!workerId.length) {

    showWorkerIdError(ERROR_WORKER_ID_IS_NULL);

    return false;

  }

  //若用户当前输入的数据和上次输入的数据一样,则不调用后台接口

  //假设用户输入123456,调用后台接口,返回结果为,不正确的工号

  //用户将输入内容进行更改后,仍然为123456,则校验程序不会访问网络,直接显示错误信息

  if (workerId == $(this).data('before')) {

    if (!isWorkerIdCorrect) {

      showWorkerIdError(ERROR_WORKER_ID_IS_NOT_CORRECT);

    }

    return false;

  }

  //调用后台接口,查询此员工id是否正确

  checkWorkerIdExists(workerId, function(data) {

    isWorkerIdCorrect = data.isWorkerIdExists;

    if (!isWorkerIdCorrect) {

      showWorkerIdError(ERROR_WORKER_ID_IS_NOT_CORRECT);

    }

  });

});

function checkWorkerIdExists(workerId, callback) {

  $.ajax({

    url: BASE_PATH + '/forgotPwd/checkWorkerIdExists.htm',

    data: {

      workerId: workerId

    },

    success: callback

  });

}

$workerIdForm.on('submit', function() {

  //只有服务器返回为true的时候,我们的表单才能提交

  if (!isWorkerIdCorrect) {

    $workerIdInput.focus();

    return false;

  }

});

上述代码写完,一个输入框的验证基本上搞定了。

我觉得还有影响用户体验的地方
还不支持回车操作,oh my god,回车也要能提交表单
若用户网速较慢,点击提交按钮,会没有任何反映,因为isWorkerIdCorrect为false,只有服务器校验成功才为true

下面是修改后的代码:

var BASE_PATH = '${rc.contextPath}';

var $workerIdInput = $('#workerIdInput');

var $workerIdError = $('#workerIdError');

//标识用户输入的工号是否正确

var isWorkerIdCorrect = false;

//标识后台校验工号是否已完成(true: 为校验中, false: 校验没开始或已结束)

var isWorkerIdLoading = false;

//标识用户是否提交了表单

var isSubmit = false;

var ERROR_WORKER_ID_IS_NULL = "员工工号不能为空";

var ERROR_WORKER_ID_IS_NOT_CORRECT = "请输入有效的员工工号";

//显示错误信息

function showWorkerIdError(errorMessage) {

  $workerIdError.html(errorMessage);

  $workerIdError.show();

}

//隐藏错误信息

$workerIdInput.on('keydown', function() {

  $workerIdError.hide();

});

//将上次输入的工号保存起来

$workerIdInput.on('focus', function() {

  var workerId = $.trim($(this).val());

  $(this).data('before', workerId);

});

//blur时进行校验

$workerIdInput.on('blur', function() {

  var workerId = $.trim($(this).val());

  //长度为0时,显示工号为空的错误信息

  if (!workerId.length) {

    showWorkerIdError(ERROR_WORKER_ID_IS_NULL);

    return false;

  }

  //若用户当前输入的数据和上次输入的数据一样,则不调用后台接口

  //假设用户输入123456,调用后台接口,返回结果为,不正确的工号

  //用户将输入内容进行更改后,仍然为123456,则校验程序不会访问网络,直接显示错误信息

  if (workerId == $(this).data('before')) {

    if (!isWorkerIdCorrect) {

      showWorkerIdError(ERROR_WORKER_ID_IS_NOT_CORRECT);

    }

    return false;

  }

  //调用后台接口,查询此员工id是否存在

  checkWorkerIdExists(workerId, function(data) {

    isWorkerIdCorrect = data.isWorkerIdExists;

    if (!isWorkerIdCorrect) {

      showWorkerIdError(ERROR_WORKER_ID_IS_NOT_CORRECT);

    }

  });

});

function checkWorkerIdExists(workerId, callback) {

  $.ajax({

    url: BASE_PATH + '/forgotPwd/checkWorkerIdExists.htm',

    data: {

      workerId: workerId

    },

    beforeSend: function() {

      //发送请求前,标识正在校验工号

      isWorkerIdLoading = true;

    },

    success: callback,

    complete: function() {

      //结束后,关闭标识

      isWorkerIdLoading = false;

      //在后台校验数据过程中,用户若提交了表单,则在此自动提交

      if (isSubmit) {

        $workerIdForm.submit();

      }

    }

  });

}

//回车提交表单

$workerIdInput.on('keypress', function(e) {

  if (e.which === 13) {

    $(this).blur();

    $workerIdForm.submit();

  }

});

$workerIdForm.on('submit', function() {

  //若正在后台校验工号,则标识用户提交了表单

  if (isWorkerIdLoading) {

    isSubmit = true;

    return false;

  }

  if (!isWorkerIdCorrect) {

    $workerIdInput.focus();

    return false;

  }

});

最终效果,图中2个输入框均为异步校验,但效果看起来和同步的一样。
图中使用了gprs网络模拟网速较慢的情况

效果图

javascript将异步校验表单改写为同步表单

Javascript 相关文章推荐
地址栏上的一段语句,改变页面的风格。(教程)
Apr 02 Javascript
jquery.jstree 增加节点的双击事件代码
Jul 27 Javascript
JS 打印界面的CSS居中代码适用所有浏览器
Mar 19 Javascript
纯js代码实现未知宽高的元素在指定元素中垂直水平居中显示
Sep 12 Javascript
Bootstrap模态对话框的简单使用
Apr 29 Javascript
JS实现将数字金额转换为大写人民币汉字的方法
Aug 02 Javascript
完美解决node.js中使用https请求报CERT_UNTRUSTED的问题
Jan 08 Javascript
vue.js实现条件渲染的实例代码
Jun 22 Javascript
vue二级路由设置方法
Feb 09 Javascript
Javascript数组方法reduce的妙用之处分享
Jun 10 Javascript
vue-dplayer 视频播放器实例代码
Nov 08 Javascript
Vue 3自定义指令开发的相关总结
Jan 29 Vue.js
JavaScript中实现sprintf、printf函数
Jan 27 #Javascript
javascript批量修改文件编码格式的方法
Jan 27 #Javascript
JavaScript中的包装对象介绍
Jan 27 #Javascript
浅谈JSON中stringify 函数、toJosn函数和parse函数
Jan 26 #Javascript
浅谈JavaScript Math和Number对象
Jan 26 #Javascript
js判断一个字符串是否包含一个子串的方法
Jan 26 #Javascript
javascript中Object使用详解
Jan 26 #Javascript
You might like
PHP 在线翻译函数代码
2009/05/07 PHP
php 多个submit提交表单 处理方法
2009/07/07 PHP
百度工程师讲PHP函数的实现原理及性能分析(二)
2015/05/13 PHP
在php中设置session用memcache来存储的方法总结
2016/01/14 PHP
php+redis实现消息队列功能示例
2019/09/19 PHP
PHP实现数组根据某个字段进行水平合并,横向合并案例分析
2019/10/08 PHP
laravel实现一个上传图片的接口,并建立软链接,访问图片的方法
2019/10/12 PHP
php实现记事本案例
2020/10/20 PHP
jquery中实现标签切换效果的代码
2011/03/01 Javascript
js导航菜单(自写)简单大方
2013/03/28 Javascript
JSON序列化与解析原生JS方法且IE6和chrome测试通过
2013/09/05 Javascript
html dom节点操作(获取/修改/添加或删除)
2014/01/23 Javascript
JavaScript中的acos()方法使用详解
2015/06/14 Javascript
jquery通过扩展select控件实现支持enter或focus选择的方法
2015/11/19 Javascript
基于jQuery实现放大镜特效
2020/10/19 Javascript
Angularjs中使用layDate日期控件示例
2017/01/11 Javascript
浅谈js中的变量名和函数名重名
2017/02/13 Javascript
js仿微博动态栏功能
2017/02/22 Javascript
bootstrap表单示例代码分享
2017/05/18 Javascript
详解VueJs前后端分离跨域问题
2017/05/24 Javascript
Angular.js中上传指令ng-upload的基本使用教程
2017/07/30 Javascript
如何使用JavaScript实现无缝滚动自动播放轮播图效果
2020/08/20 Javascript
vue中解决微信html5原生ios虚拟键返回不刷新问题
2020/10/20 Javascript
Python完全新手教程
2007/02/08 Python
python类的方法属性与方法属性的动态绑定代码详解
2017/12/27 Python
Python实现按中文排序的方法示例
2018/04/25 Python
PYQT5设置textEdit自动滚屏的方法
2019/06/14 Python
Python基于pip实现离线打包过程详解
2020/05/15 Python
Kears 使用:通过回调函数保存最佳准确率下的模型操作
2020/06/17 Python
易程科技软件测试笔试
2013/03/24 面试题
教师个人查摆剖析材料
2014/10/14 职场文书
个人收入证明格式
2015/06/24 职场文书
小学六一儿童节活动开幕词
2016/03/04 职场文书
CocosCreator ScrollView优化系列之分帧加载
2021/04/14 Python
python中__slots__节约内存的具体做法
2021/07/04 Python
十大最强飞行系宝可梦,BUG燕上榜,第二是飞行系王者
2022/03/18 日漫