javascript面向对象系列讲解之Tab切换实战。声明:为了方便大家学习和查看,所以特意控制了文章的篇幅,将面向对象写成了多篇连续博文的方式,也方便大家根据自己具体情况进行选择性的学习。
在上一篇文章当中,我们讲解了混合模式的书写方法,解释了如何使用new去解决这种工厂模式的缺陷,如何利用原型解决“方法”的重复创建。本文我将以Tab切换为实例,为大家讲解如何一步步将自己的代码修改为面向对象的代码。
进行基本结构和样式搭建:
- <!doctype html>
- <html>
- <head>
- <meta charset=”UTF-8″>
- <title>面向对象-独行冰海</title>
- <style>
- .tit span{
- float: left;
- width: 100px;
- background: #ccf;
- }
- .tit .select{
- background: #99f;
- }
- .con div{
- display: none;
- width: 300px;
- height: 200px;
- background: #cfc;
- }
- .con .show{
- display: block;
- }
- </style>
- </head>
- <body>
- <div id=’tabTit’>
- <span class=’select’>1</span>
- <span>2</span>
- <span>3</span>
- </div>
- <div class=’con’ id=’tabCon’>
- <div class=’show’>1</div>
- <div>2</div>
- <div>3</div>
- </div>
- </body>
- <script>
- var tabTit = document.getElementById(‘tabTit’).getElementsByTagName(‘span’);
- var tabCon = document.getElementById(‘tabCon’).getElementsByTagName(‘div’);
- for (var i = 0; i < tabTit.length; i++) {
- tabTit[i].index = i;
- tabTit[i].onclick = function(){
- for (var i = 0; i < tabTit.length; i++) {
- tabTit[i].className = ”;
- tabCon[i].className = ”;
- };
- this.className = ‘select’;
- tabCon[this.index].className = ‘show’;
- }
- };
- </script>
- </html>
第一步,不要出现函数中嵌套着函数,将函数提取出来(注意,上面用了不同于自己之前书写的tab的一种写法,为每个元素创建了一个属性index,存储索引值)
拆分后:
- <script>
- var tabTit = document.getElementById(‘tabTit’).getElementsByTagName(‘span’);
- var tabCon = document.getElementById(‘tabCon’).getElementsByTagName(‘div’);
- for (var i = 0; i < tabTit.length; i++) {
- tabTit[i].index = i;
- tabTit[i].onclick = tabFun;
- };
- function tabFun(){
- for (var i = 0; i < tabTit.length; i++) {
- tabTit[i].className = ”;
- tabCon[i].className = ”;
- };
- this.className = ‘select’;
- tabCon[this.index].className = ‘show’;
- }
- </script>
第2步,创建构造函数、函数变方法、变量变属性、设置基本参数:
- /*
- *
- * 创建构造函数
- *
- */
- function TabSwitch(titId, titEle, conId, conEle){
- this.tabTit = document.getElementById(titId).getElementsByTagName(titEle);
- this.tabCon = document.getElementById(conId).getElementsByTagName(conEle);
- for (var i = 0; i < this.tabTit.length; i++) {
- this.tabTit[i].index = i;
- this.tabTit[i].onclick = this.tabFun;
- }
- }
- TabSwitch.prototype.tabFun = function(){
- // 在这里,this指向发生了变化
- for (var i = 0; i < this.tabTit.length; i++) {
- this.tabTit[i].className = ”;
- this.tabCon[i].className = ”;
- };
- this.tabTit[i].className = ‘select’;
- this.tabCon[this.tabTit[i].index].className = ‘show’;
- }
- new TabSwitch(‘tabTit’, ‘span’, ‘tabCon’, ‘div’);
第3步,修改调用方法,防止this指向有误,将方法提取到外部,利用原型进行书写,同时注意参数的传递:
- function TabSwitch(titId, titEle, conId, conEle){
- var _this = this;
- this.tabTit = document.getElementById(titId).getElementsByTagName(titEle);
- this.tabCon = document.getElementById(conId).getElementsByTagName(conEle);
- for (var i = 0; i < this.tabTit.length; i++) {
- this.tabTit[i].index = i;
- this.tabTit[i].onclick = function(){
- // 调用的应当是tabSwitch的方法
- // 传递的应该是被点击的这个元素
- _this.tabFun(this);
- }
- }
- }
- TabSwitch.prototype.tabFun = function(objTab){
- for (var i = 0; i < this.tabTit.length; i++) {
- this.tabTit[i].className = ”;
- this.tabCon[i].className = ”;
- };
- objTab.className = ‘select’;
- this.tabCon[objTab.index].className = ‘show’;
- }
- new TabSwitch(‘tabTit’, ‘span’, ‘tabCon’, ‘div’);
到此为止,我们的tab切换的面向对象代码已经构建完成了,当然如果使用了不同的结构,tab切换具体的内容也要进行相应的调整。个人比较推荐的结构如下:
- <div id=’tabTit’>
- <span class=’select’>1</span>
- <span>2</span>
- <span>3</span>
- </div>
- <div class=’con’ id=’tabCon’>
- <div class=’show’>1</div>
- <div>2</div>
- <div>3</div>
- </div>
这样的基本结构,我们可以直接使用children(在获取标签的时候),而不需要进行4个参数的传递,只需要传递tabTit和tabCon即可。这样也更有利于我们代码的扩展性和重用性。
在下一篇文章当中,我将继续为大家讲解面向对象的基本知识,将采用拖拽作为实例进行面向对象的讲解,之所以使用拖拽,目的在于给大家介绍一下面向对象中的“继承”的基本知识和用法。请关注下一篇文章——面向对象系列——拖拽(继承知识)实战