原生Js与jquery的多组处理, 仅展开一个区块的折叠效果


Posted in Javascript onJanuary 09, 2011

需求是, 同一个页面, 有多组(不固定), 每组区块数量不一定一样的小区块. 要求每次只展开一个区块. 实现原理其实很简单, 点击导航, 若它的区块为隐藏, 则展开它, 同时, 隐藏掉同组其他区块; 若它的区块为展开, 则隐藏它, 同时, 展开同组其他区块中的一个. 一开始以为仅仅简单的两个遍历就能搞定. 但事实并非如此. 冷静思考了下, 通过点击的元素取到当前组的相关元素, 再单独处理当前组才合理. 顺着这个思路, 功能终于实现了, 写了原生Js版本, 用同样的思路写了个jQ版本. 时间关系, 写的也比较零散, 就没有封装. 其实, 对这种思路也不是很满意, 感觉太散了, 哪位大师有更好的思路请赐教.
原生Js与jquery的多组处理, 仅展开一个区块的折叠效果
jQ版区块的标题, 会有一个Js错误, 那是因为获取Js版下的h2时, 我偷了个懒, 把jQ的也遍历进去了. 我想, 实际应用中, 也不会有人同一个效果, 一边用Js一边用jQ吧. 核心代码点此查看样例

//原生Js版本 ***** start 
window.onload=function(){ 
//共用函数区 
var iBase={ 
//document.getElementById 
Id: function(name){return document.getElementById(name)}, 
//通过class获取元素 
GetByClass: function(name,tagName,elem){ 
var c=[]; 
var re=new RegExp('(^|\\s)'+name+'(|\\s$)'); 
var e=(elem || document).getElementsByTagName(tagName || '*'); 
for(var i=0; i < e.length; i++){ 
if(re.test(e[i].className)){ 
c.push(e[i]); 
} 
} 
return c; 
}, 
//获取样式属性 
AttrStyle: function(elem,attr){ 
if(elem.attr){ 
return elem.style[attr]; 
}else if(elem.currentStyle){ 
return elem.currentStyle[attr]; 
}else if(document.defaultView && document.defaultView.getComputedStyle){ 
attr=attr.replace(/([A-Z])/g,'-$1').toLowerCase(); 
return document.defaultView.getComputedStyle(elem,null).getPropertyValue(attr); 
}else{ 
return null; 
} 
}, 
//获取祖辈元素中符合指定样式的元素 
Parents: function(elem,name){ 
var r=new RegExp('(^|\\s)'+name+'(|\\s$)'); 
elem=elem.parentNode; 
if(elem!=null){ 
return r.test(elem.className) ? elem : iBase.Parent(elem,name) || null; 
} 
}, 
//取索引值 
Index: function(cur,obj){ 
for(var i=0; i < obj.length; i++){ 
if(obj[i]==cur){ 
return i; 
} 
} 
} } 
//变量定义 
var listBox=iBase.GetByClass('js','div'); 
var navItem=iBase.Id('demo').getElementsByTagName('h2');//此处将jQ区块中的h2也取到了,所以页面会有个小小的错误 
var icoItem=null,boxItem=null,boxDisplay=null,elemIndex=null,elemParent=null; 
//初始化展开第一个 
for(var i=0; i < listBox.length;i++){ 
iBase.GetByClass('box','div',listBox[i])[0].style.display='block'; 
listBox[i].getElementsByTagName('span')[0].innerHTML='-'; 
} 
//遍历所有点击项 
for(var i=0; i < navItem.length;i++){ 
navItem[i].onclick=function(){ 
elemParent=iBase.Parents(this,'js');//获取当前点击所在区块 
navItem=elemParent.getElementsByTagName('h2');//获取当前区块下的点击项 
icoItem=elemParent.getElementsByTagName('span');//获取当前区块下的展开关闭 
boxItem=iBase.GetByClass('box','div',elemParent);//获取需要控制的区块 
elemIndex=iBase.Index(this,navItem);//获取当前点击在当前区块点击项中的索引 
//切换展开关闭图标 
icoItem[elemIndex].innerHTML= icoItem[elemIndex].innerHTML=='-' ? '+' : '-'; 
if(iBase.AttrStyle(boxItem[elemIndex],'display')=='block'){ 
//控制项展开状态下,隐藏当前,展开其他的第一项 
//此处有个展开0/1的判断,因为当点击第一个时是不能再展开第一个的 
boxItem[elemIndex].style.display='none'; 
if(elemIndex==0){ 
boxItem[1].style.display='block'; 
icoItem[1].innerHTML='-' 
}else{ 
boxItem[0].style.display='block' 
icoItem[0].innerHTML='-' 
} 
}else{ 
//控制项展开状态下,展开当前,隐藏其他项 
boxItem[elemIndex].style.display='block'; 
for(var k=0;k < boxItem.length; k++){ 
if(k!=elemIndex){ 
boxItem[k].style.display='none'; 
icoItem[k].innerHTML='+'; 
} 
} 
} 
} 
} 
} 
//jQuery版本 ***** start 
$(function(){ 
//变量定义区 
var _listBox=$('.jq'); 
var _navItem=$('.jq>h2'); 
var _boxItem=null, _icoItem=null, _parents=null, _index=null; 
//初始化第一个展开 
_listBox.each(function(i){ 
$(this).find('div.box').eq(0).show(); 
$(this).find('h2>span').eq(0).text('-'); 
}); 
//遍历所有的点击项 
_navItem.each(function(i){ 
$(this).click(function(){ 
//找到当前点击父元素为listbox(单个区块)的元素 
_parents=$(this).parents('.listbox'); 
_navItem=_parents.find('h2');//此区块中的点击项 
_icoItem=_parents.find('span');//此区块中的展开关闭图标 
_boxItem=_parents.find('div.box');//此区块中展开关闭项 
_index=_navItem.index(this);//取得当前点击在当前区块下点击项中的索引值 
if(_boxItem.eq(_index).is(':visible')){ 
//若当前点击项下的展开关闭项是显示的,则关闭,同时展开另外项中的第一个 
_boxItem.eq(_index).hide().end().not(':eq('+_index+')').first().show(); 
_icoItem.eq(_index).text('+').end().not(':eq('+_index+')').first().text('-'); 
}else{ 
//若当前点击项下的展开关闭项是隐藏的,则展开,同时隐藏其他项 
_boxItem.eq(_index).show().end().not(':eq('+_index+')').hide(); 
_icoItem.eq(_index).text('-').end().not(':eq('+_index+')').text('+'); 
} 
}); 
}); 
});

演示地址:http://demo.3water.com/js/jsjq-flod-onlyone/index.htm
打包下载:https://3water.com/jiaoben/33950.html
本人来自Mr.Think的博客 http://mrthink.net/jsjq-flod-onlyone/
Javascript 相关文章推荐
jQuery 技巧大全(新手入门篇)
May 12 Javascript
javascript开发技术大全-第3章 js数据类型
Jul 03 Javascript
JS实现下拉框的动态添加(附效果)
Apr 03 Javascript
浅谈js中的闭包
Mar 16 Javascript
js判断radiobuttonlist的选中值显示/隐藏其它模块的实现方法
Aug 25 Javascript
详解Vue2.0 事件派发与接收
Sep 05 Javascript
Vue组件中slot的用法
Jan 30 Javascript
Node如何后台数据库使用增删改查功能
Nov 21 Javascript
Vue学习之axios的使用方法实例分析
Jan 06 Javascript
40行代码把Vue3的响应式集成进React做状态管理
May 20 Javascript
js前端传json后台接收‘‘被转为quot的问题解决
Nov 12 Javascript
使用jquery实现轮播图效果
Jan 02 jQuery
JS中动态添加事件(绑定事件)的代码
Jan 09 #Javascript
jquery的extend和fn.extend的使用说明
Jan 09 #Javascript
js对象之JS入门之Array对象操作小结
Jan 09 #Javascript
理解JavaScript中的对象 推荐
Jan 09 #Javascript
最佳JS代码编写的14条技巧
Jan 09 #Javascript
JavaScript定义类或函数的几种方式小结
Jan 09 #Javascript
javascript中用星号表示预录入内容的实现代码
Jan 08 #Javascript
You might like
Server.HTMLEncode让代码在页面里显示为源代码
2013/12/08 PHP
PHP getNamespaces()函数讲解
2019/02/03 PHP
小议Javascript中的this指针
2010/03/18 Javascript
解决iframe的frameborder在chrome/ff/ie下的差异
2010/08/12 Javascript
始终在屏幕中间显示Div的代码(css+js)
2011/03/10 Javascript
使用GruntJS链接与压缩多个JavaScript文件过程详解
2013/08/02 Javascript
JQuery实现Ajax加载图片的方法
2015/12/24 Javascript
JS代码实现百度地图 画圆 删除标注
2016/10/12 Javascript
原生javascript移动端滑动banner效果
2017/03/10 Javascript
微信小程序实现给循环列表添加点击样式实例
2017/04/26 Javascript
最全正则表达式总结:验证QQ号、手机号、Email、中文、邮编、身份证、IP地址等
2017/08/16 Javascript
JavaScript实现的DOM树遍历方法详解【二叉DOM树、多叉DOM树】
2018/05/07 Javascript
Vue中JS动画与Velocity.js的结合使用
2019/02/13 Javascript
浅谈Vuex的this.$store.commit和在Vue项目中引用公共方法
2020/07/24 Javascript
vue 动态生成拓扑图的示例
2021/01/03 Vue.js
Python内置函数之filter map reduce介绍
2014/11/30 Python
Python比较文件夹比另一同名文件夹多出的文件并复制出来的方法
2015/03/05 Python
用ReactJS和Python的Flask框架编写留言板的代码示例
2015/12/19 Python
深入理解Django中内置的用户认证
2017/10/06 Python
pandas的连接函数concat()函数的具体使用方法
2019/07/09 Python
Python 用turtle实现用正方形画圆的例子
2019/11/21 Python
Tensorflow tensor 数学运算和逻辑运算方式
2020/06/30 Python
HTML5样式控制示例代码
2013/11/27 HTML / CSS
澳大利亚珍珠首饰购物网站:Vayo Pearls
2019/03/11 全球购物
荷兰在线钓鱼商店:Raven
2019/06/26 全球购物
英国领先的独立时装店:Van Mildert
2019/10/28 全球购物
转让协议书范本
2014/04/15 职场文书
教师教学评估方案
2014/05/09 职场文书
党政领导班子四风问题对照检查材料思想汇报
2014/10/02 职场文书
领导班子四风问题个人对照检查材料
2014/10/04 职场文书
2015关于重阳节的演讲稿
2015/03/20 职场文书
逃课检讨书范文
2015/05/06 职场文书
地球上的星星观后感
2015/06/02 职场文书
2016党员发展对象培训心得体会
2016/01/08 职场文书
职场中的你,辞职信写对了吗?
2019/06/26 职场文书
Python 读写 Matlab Mat 格式数据的操作
2021/05/19 Python