task0002(四)- 练习:数据处理、轮播及交互
包括5部分:
源码地址 小练习1:处理用户输入
任务描述在 第一阶段在页面中,有一个单行输入框,一个按钮,输入框中用来输入用户的兴趣爱好,允许用户用半角逗号来作为不同爱好的分隔。 当点击按钮时,把用户输入的兴趣爱好,按照上面所说的分隔符分开后保存到一个数组,过滤掉空的、重复的爱好,在按钮下方创建一个段落显示处理后的爱好。 实现 根据题目要求,这个地方比较简单,可以直接利用前面写过的一些函数,分成四步,进行。
html: <input type="text" id="user_input"> <button id="btn">提交</button> <ul id="user_output"></ul>
//自执行的匿名函数 (function handle_1() { //其实这里没必要使用id因为数据那么少$函数直接获取标签就行 var inp = $("#user_input"); var out = $("#user_output"); $.click("#btn",function () { var value = inp.value.split(/,|,/); //1.根据半角逗号分割成数组。 var unValue = uniqArray(value); //2.数组去重 for (var i = 0,len = unValue.length; i < len; i++) { var trimValue = trim(unValue[i]); //3.对每一项进行去除首尾空格操作 console.log(trimValue); if (trimValue !== "") { //4.只有在去除首尾空格后不为空的数组才输出。 out.innerHTML += "<li>" + trimValue + "</li>" } } }) })(); 第二阶段单行变成多行输入框,一个按钮,输入框中用来输入用户的兴趣爱好,允许用户用换行、空格(全角/半角)、逗号(全角/半角)、顿号、分号来作为不同爱好的分隔。 当点击按钮时的行为同上 实现 看题目描述,主要是对于第一步进行修改,第一阶段只要求对半角逗号进行处理,但是在第二阶段中,需要对“换行、空格(全角/半角)、逗号(全角/半角)、顿号、分号”进行处理。 只需要对
第三阶段用户输入的爱好数量不能超过10个,也不能什么都不输入。当发生异常时,在按钮上方显示一段红色的错误提示文字,并且不继续执行后面的行为;当输入正确时,提示文字消失。 同时,当点击按钮时,不再是输出到一个段落,而是每一个爱好输出成为一个checkbox,爱好内容作为checkbox的label。 实现
最终完成html: <textarea name="user_input" id="user_input" cols="45" rows="10"></textarea> <br> <button id="btn">处理并输出</button> <p>输入的爱好数量不能超过10个,或什么都不输入</p> <form id="user_output"></form> js: (function handle_1() { var inp = $("#user_input"); var out = $("#user_output"); $.click("#btn",function () { var value = inp.value.split(/n|s+|,|,|、|;|;/); //分割成数组。 var unValue = uniqArray(value); //数组去重 var i = 0; var len = unValue.length; if (len > 10 || unValue == "") { $("p").style.disautoPlay = "block"; } else { $("p").style.disautoPlay = "none"; for (; i < len; i++) { var trimValue = trim(unValue[i]); //对每一项进行去除首尾空格操作 console.log(trimValue); if (trimValue !== "") { //只有在去除首尾空格后不为空的数组才输出。 out.innerHTML += "<label>" + "<input type='checkbox'>" + trimValue + "</label>" } } } }) })(); 在线演示:小练习1:处理兴趣列表 小练习2:日期对象的使用任务描述在和上一任务同一目录下面创建一个
实现思路了解日期对象这里主要是考察的对于日期对象的使用。
//时间对象创建的几种方式。 var today = new Date(); var birthday = new Date("December 17,1995 03:24:00"); var birthday = new Date("1995-12-17T03:24:00"); var birthday = new Date(1995,11,17); var birthday = new Date(1995,17,3,24,0);
正式开始:
给按钮添加点击事件,在点击时,调用刚刚编写的的时间处理函数。 在线演示:小练习2:倒计时 小练习3:轮播图组件任务描述在和上一任务同一目录下面创建一个
效果示例:http://echarts.baidu.com/ 上面的轮播图(不需要做左右两个箭头) 实现思路:
该轮播图有依赖函数。主要使用到以下函数:
第一步:实现点击切换编写幻灯片函数:
function Slideshow(element) { //1.创建li var imgArr = element.getElementsByTagName("img"); //获取图片数量 var imgArrLen = imgArr.length; //缓存图片数量 var createUl = document.createElement("ul"); //创建小点的ul var iCurrent = parseInt(getStyle(imgArr[0],"width")); //获取一张图片的宽度 element.style.width = iCurrent * imgArrLen + "px"; //设置图片容器的宽度。 //创建li for (var i = 0,len = imgArrLen; i < len; i++) { createUl.innerHTML += "<li></li>"; } element.parentNode.appendChild(createUl); //插入导航 addClass(createUl,"Slideshow-nav"); //添加导航样式 addClass(createUl.getElementsByTagName("li")[0],"active"); //默认设置第一个为第当前活动的li //编写点击函数clickLi: clickLi(); /** * 点击导航 */ function clickLi() { delegateEvent(createUl,"li","click",function () { var iTaget = -iCurrent * getIndex(this); removeLiClass(); addClass(this,"active"); //移出 startMove(element,{ "left": iTaget }); }); } /** * 用于移除所有的Li的选中状态:active */ function removeLiClass() { var oLi = createUl.getElementsByTagName("li"); for (var i = 0,len = oLi.length; i < len; i++) { removeClass(oLi[i],"active"); } } } 第二步:实现自动播放
这里我们的最基本的功能都实现了,代码如下:(放在 var iSpeed = 4000;//定时器间隔。 hoverElement(); /* * 移入图片容器暂停,移除继续播放。 */ function hoverElement() { addEvent(element.parentNode,"mouSEOver",function () { clearInterval(timer); }); addEvent(element.parentNode,"mouSEOut",function () { timer = setInterval(autoPlay,iSpeed); }); } var timer = null; timer = setInterval(autoPlay,iSpeed); /* * 自动播放函数。 */ function autoPlay() { var heightLi = $(".Slideshow-nav .active"); //高亮的li var iTaget; iTaget = (getIndex(heightLi) + 1) === imgArrLen ? 0 : (-iCurrent * (getIndex(heightLi) + 1)); if (getIndex(heightLi) + 1 === imgArrLen - 1) { clearInterval(timer); } var nextLi = heightLi.nextElementSibling; if (nextLi) { removeLiClass(); addClass(nextLi,"active"); } startMove(element,{ "left": iTaget }); } 第三步:添加配置项(题目要求完成)
/* * @param {JSON} option 配置项 * @config {String} noLoop 不循环?,默认为循环,只要存在则不循环,任意值 * @config {String} reverse 是否反向,任意值。只有“noLoop”不存在时,也就是只有循环时,才执行。 * @config {Number} intervalTime 轮播间隔时间(单位为毫秒),默认为4000, */
//在下一个元素节点不存在的情况下(也就是到了最后了),设置第一个节点为活动状态,就这样正向的循环就成功了! else { removeLiClass(); addClass($(".Slideshow-nav li"),"active"); }
其实到这里我们题目要求就完成了! 但是!不挑战一下怎么能行? 为什么不把左右点击切换一起实现了呢? 既然这样,我们就继续吧! 第四步:扩展!左右箭头实现!
//创建左右导航 var createSpan = document.createElement("div"); addClass(createSpan,"left-right") createSpan.innerHTML = "<span class='nav-left'><</span><span class='nav-right'>></span>" element.parentNode.appendChild(createSpan);
delegateEvent(createSpan,"span",function () { var heightLi = $(".Slideshow-nav .active"); //高亮的待选li var leftIndex = !getIndex(this); //点击左时为true,点击又为false //移动的目标值,默认正向 play(leftIndex); }); 至此,我们的轮播图组件就完成了! 需要配合CSS使用。 通过这次封装,收益良多,感兴趣的话可以看看源码 在线演示:小练习3:图片轮播组件 小练习4:输入提示框任务描述在和上一任务同一目录下面创建一个 要求如下:
初级班:
var suggestData = ['Simon','Erik','Kener']; 中级班:
示例: 实现思路这里我并没有一开始就直接进行数据获取的部分,而是进行了任务分解,如下: 第一阶段
第二阶段
在线演示:小练习4:输入框即时提示 小练习5:界面拖拽交互
实现思路:第一步:封装拖拽函数
/** * 鼠标拖拽函数。 * @param {HTMLElement} element 需要拖拽的对象 */ function setDrag(element) { addEvent(element,"mousedown",onmousedown); //鼠标按下 function onmousedown(ev) { var oEvent = ev || event; var disX = oEvent.clientX - this.offsetLeft; var disY = oEvent.clientY - this.offsetTop; var that = this; addEvent(document,"mousemove",onmousemove); addEvent(document,"mouseup",onmouseup); /** * 鼠标移动 */ function onmousemove(ev) { var oEvent = ev || event; that.style.left = oEvent.clientX - disX + "px"; that.style.top = oEvent.clientY - disY + "px" } /** * 鼠标抬起删除事件 */ function onmouseup() { removeEvent(document,onmousemove); removeEvent(document,onmouseup); } } } 第二步:布局转换函数
/** * 布局转换函数 * @param {HTMLElment} element HTML对象 * @param {string} childEle 其内需要转换的标签名 */ function toPosition(element,childEle) { var eleArr = element.getElementsByTagName(childEle); var aPos = []; // for (var i = 0,len = eleArr.length; i < len; i++) { aPos[i] = { left: eleArr[i].offsetLeft,top: eleArr[i].offsetTop }; } for (var i = 0,len = eleArr.length; i < len; i++) { eleArr[i].style.left = aPos[i].left + "px"; eleArr[i].style.top = aPos[i].top + "px"; eleArr[i].style.position = "absolute"; eleArr[i].style.margin = "0"; } } 在线演示:小练习5:拖拽交互 第三步:实现拖拽
但是,为什么不用事件代理呢? 特别简单,只需要对上面写的函数进行一些简单的改装。 delegateEvent(parentElement,function (ev) { //此处是原函数中的内容。 } 现在知道为什么上面的函数会用到this了吧? 第四步:碰撞检测函数先来看张图: 是不是有瞬间豁然开朗的感觉呢? 获取相关值,只需要考虑不碰不上的情况就行了!。如下: /** * 碰撞检测函数 * @param {object} obj1 对象1 * @param {object} obj2 对象2 * @returns {boolean} 碰撞时返回true,否则反正false */ function hitDetection(obj1,obj2) { //对象1的相关值 var l1 = obj1.offsetLeft; var r1 = obj1.offsetLeft + obj1.offsetWidth; var t1 = obj1.offsetTop; var b1 = obj1.offsetTop + obj1.offsetHeight; //对象2的相关值 var l2 = obj2.offsetLeft; var r2 = obj2.offsetLeft + obj2.offsetWidth; var t2 = obj2.offsetTop; var b2 = obj2.offsetTop + obj2.offsetHeight; if (r1 < l1 || l1 > r2 || b1 < t2 || t1 > b2) { return false;//没碰上 } else { return true; } } 第五步:处理各种碰撞情况
(编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |