使用AJAX发送表单信息
为什么要使用AJAX发送表单数据?
因为使用表单发送时,一旦失败,错误信息总会显示在第二个页面内。用户体验不好。
使用AJAX发送时,一旦失败,错误信息显示在本页。用户可以不必其它操作,直接修改即可。
表单序列化
如果使用表单本身去提交,数据都是浏览器帮忙组织的。
使用AJAX提交表单数据时,只能够自己组织数据。
一个两个表单控件,好说,一两个表单也好说。但是,总会出现新的表单,表单的结构总会变化。此时,自己一个一个的组装数据会显得很麻烦。于是我们定义一个函数,让函数帮助我们把表单中的数据给序列化好。
表单序列化的应用场景: 使用AJAX提交整个表单的数据
为什么要表单序列化: 没有人帮助我们组织表单中的数据
jQuery中的序列化函数
$(form).serialize();
返回值:form中所有控件的key与value组成的字符串
demo:
$("form").serialize();
console:
自己封装的序列化函数
举例:
// 定义函数 该函数接收一个表单元素作为参数 返回的是该表单元素的所有控件名与控件值组成的字符串
function serialize(form) {
// 定义字符串
var str = '';
// 获取所有的表单控件
// var elements = form.elements;
var elements = form.getElementsByTagName("*");
// 将所有带有name属性的控件过滤出来
var arr = [];
// 循环所有的elements
for(var i = 0; i < elements.length; i++) {
// 判定是否具备name属性
if (elements[i].name) {
arr.push(elements[i]);
}
}
// 挨个匹配
for(var i = 0; i < arr.length; i++) {
if (arr[i].type === "text" || arr[i].type === "password" || arr[i].type === "select-one" || arr[i].type === "textarea" ) {
str += arr[i].name + "=" + encodeURIComponent(arr[i].value) + "&";
} else if (arr[i].type === "radio" && arr[i].checked) {
str += arr[i].name + "=" + encodeURIComponent(arr[i].value) + "&";
}
}
str = str.slice(0, -1);
return str;
}
转码
因为URL上不可以有中文,所以需要转码。
转码函数
encodeURIComponent是一个转码函数,作用就是转码
有如下字符串
var str = "username=王老五&password=123&sex=male&age=18&suggest=aaaa"
进行转码:
var str1 = encodeURIComponent(str);
转码结果:
解码函数
decodeURIComponent 该函数用于解码
有已经转码的字符串如下:
var str = "username=%E7%8E%8B%E8%80%81%E4%BA%94&password=123&sex=male&age=18"
解码:
var result = decodeURIComponent(str);
解码结果:
"username=王老五&password=123&sex=male&age=18"
一、瀑布流
瀑布流指的是一种页面模型。
特点是随着用户浏览页面,页面会一直往下撑开。像瀑布一样。
瀑布流布局
我们发现,花瓣网的瀑布流属于定宽瀑布流,每一个列的宽度都是相等的。
我们找了99个图片,探讨一下布局方式
代码1:
var lis = document.getElementsByTagName("li");
for(var i = 0; i < 100; i++) {
var img = new Image();
img.src = "img/" + i + ".png";
lis[i % 3].appendChild(img)
}
结论:发现因为每一个图片的高度不一致,所以导致页面的底部不平。
改进:按照高度去上树
// 我们现在决定按照高度上树
var lis = document.getElementsByTagName("li");
// 定义一个高度映射数组
var arr = new Array(lis.length).fill(0);
// 循环
for(var i = 0; i < 100; i++) {
var img = new Image();
img.src = "img/" + i + ".png";
img.onload = function() {
// 获取数组中的最小项的下标
var idx = getMinIdx(arr);
// 找到对应的li
lis[idx].appendChild(this);
// 图片已经上树 li的高度发生了变化 li的映射数组的值也应当发生变化
arr[idx] += this.height;
}
}
// 定义函数 获取数组中最小的值的下标
function getMinIdx(arr) {
var idx = 0;
var min = arr[idx];
for(var i = 1; i < arr.length; i++) {
if (min > arr[i]) { // 如果最小值比下一个数值还要大 那么应该更换最小值 并 更换下标值
min = arr[i];
idx = i;
}
}
return idx;
}
上树方式
AJAX请求回来数据之后,想要将这些内容上树,让用户看到。有多种方式。
第一种上树方式
有几个元素 ,就创建几个元素。
缺点:代码太多。
第二种上树方式
不论一个结构内有几个元素,只创建最外层元素。将内层元素作为外层元素的innerHTML来拼接。
优点:比第一种好
缺点:当dom结构复杂时,不好分清楚结构。
第三种上树方式
使用模板引擎方式。
定义模板: 将内容写在一个不可以执行的script标签内
<script type="text/template" id="tpl">
<div class="container">
<div class="item">
<span>用户名</span><span><%username%></span>
</div>
<div class="item">
<span>性别</span><span><%sex%></span>
</div>
<div class="item">
<span>年龄</span><span><%age%></span>
</div>
<div class="item">
<div class="type">
<span>卡片类型</span><span><%card.type%></span>
</div>
<div class="num">
<span>卡片号码</span><span><%card.number%></span>
</div>
<div class="yue">
<span>余额</span><span><%card.money%></span>
</div>
</div>
</div>
</script>
定义字典: AJAX请求回来的数据
{
"error": 0,
"data": {
"username": "wanglaowu",
"age": 13,
"sex": "nan",
"card": {
"type": "招商银行",
"number": 19823619823173,
"money": 25
}
}
}
格式化: 将模板与字典结合。
// 定义一个函数 该函数接收两个参数 第一个是模板字符串 第二个是对象
function format(tplStr, dictionary) {
// 替换方法 将字符串中某些内容替换掉
return tplStr.replace(/<%((\w+)(\.\w+)*)%>/g, function(match, $1) {
// 将$1以.分割成数组
var arr = $1.split(".");
var result = dictionary;
// 循环arr 从dictionary中获取数据
for(var i = 0; i < arr.length - 1; i++) {
result = result[arr[i]];
}
return result[arr[i]];
})
}
调用
var str_format = format(str, data.data)
上树:上树
msg.html(str_format)
underscore
这是一个JS实用库。变量名是下划线: _
里面有许多的函数式编程风格的功能。
这里只介绍_.template函数
该函数用于格式化模板
第一步: 将定义好的字符串模板放入该函数
// 定义字符串模板
var tpl_str = "<div><%=name%></div>"
// 生成函数
var format = _.template(tpl_str);
此时,format就是一个函数,该函数与tpl_str字符串模板绑定。只要想生成tpl_str结构的模板,就调用format并传递字典。
第二步:调用format并传递字典
format({name: "王老五"})
第三步:结果
<div>王老五</div>
underscore: 这是一个JS工具库包含了许多JS的常用方法例如filter、map、reduce、some等