大熊君JavaScript插件化开发------(实战篇之DXJ UI ------ Tab功能扩展完结版)

本文主要是介绍大熊君JavaScript插件化开发------(实战篇之DXJ UI ------ Tab功能扩展完结版),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

一,开篇分析

Hi,大家好!大熊君又和大家见面了,还记得上一篇文章吗。主要讲述了一个“Tab”插件是如何组织代码以及实现的”,以及过程化设计与面向对象思想设计相结合的方式是

如何设计一个插件的,两种方式各有利弊取长补短,本系列文章是以学习为导向的,具体场景大家自己定夺使用方式。在从这篇文章中,我们还是以那个“Tab”实例为主,

继续扩展相关功能。嘿嘿嘿,废话少说,进入正题。直接上实际效果图:

  

大家看到了吧,增加了一个新的功能,如果我们在初始化时,我们的模块配置信息项目的条目数大于我们指定的,那么就会显示在“更多模块”

操作项的隐藏列表中,我们的初始化参数配置也从新做了调整比如多了一个“displayMax”指定初始化时的条目数,还有一个项目属性,“status”

在初始化时也去掉了不需要配置了,在程序中动态生成配置,增加了程序的灵活性,下面就具体分析一下吧。

 

(二),实例分析

(1),首先确定这个插件做什么事。下面看一下插件的调用方式,以及配置参数说明。如下代码:

  

 1 {
 2     buttonText : "添加模块" ,
 3     result : [ 
 4         {
 5             text : "向导提示" ,
 6             url : "help.html" ,
 7             showClose : "0"
 8         } ,
 9         {
10             text : "学生信息" ,
11             url : "info.html" ,
12             showClose : "1"
13         } ,
14         {
15             text : "学生分类" ,
16             url : "category.html" ,
17             showClose : "1"
18         } ,
19         {
20             text : "大熊君{{bb}}" ,
21             url : "bb.html" ,
22             showClose : "1"
23         } ,
24         {
25             text : "Beta测试模块" ,
26             url : "test.html" ,
27             showClose : "1"
28         } ,
29         {
30             text : "三胖子" ,
31             url : "help.html" ,
32             showClose : "1"
33         } ,
34         {
35             text : "四秃子" ,
36             url : "help.html" ,
37             showClose : "1"
38         }
39     ] ,
40     displayMax : 5 // 最多显示项目
41 }    

 

  

“bigbear.ui.createTab”里面包含两个参数,第一个是dom节点对象,第二个是插件参数选项,"buttonText "代表“Tab“插件中,操作按钮的文字描述。

”result“是一个数组,里面包含的是选项卡项目的属性,包括文字描述,点击选项卡项目时做请求使用的url,”showClose“代表选项卡的选项是否显示关闭按钮。

“status”在初始化时也去掉了不需要配置了,在程序中动态生成配置。可能会有关闭状态,分别表示为:1-默认显示,0-关闭状态,2-超过默认的条目数。

 

(2),功能分步骤介绍

1---,通过可选参数,初始化插件:

  

 1 $(function(){
 2     bigbear.ui.createTab($("#tab"),{
 3         buttonText : "添加模块" ,
 4         result : [ 
 5             {
 6                 text : "向导提示" ,
 7                 url : "help.html" ,
 8                 showClose : "0"
 9             } ,
10             {
11                 text : "学生信息" ,
12                 url : "info.html" ,
13                 showClose : "1"
14             } ,
15             {
16                 text : "学生分类" ,
17                 url : "category.html" ,
18                 showClose : "1"
19             } ,
20             {
21                 text : "大熊君{{bb}}" ,
22                 url : "bb.html" ,
23                 showClose : "1"
24             } ,
25             {
26                 text : "Beta测试模块" ,
27                 url : "test.html" ,
28                 showClose : "1"
29             } ,
30             {
31                 text : "三胖子" ,
32                 url : "help.html" ,
33                 showClose : "1"
34             } ,
35             {
36                 text : "四秃子" ,
37                 url : "help.html" ,
38                 showClose : "1"
39             }
40         ] ,
41         displayMax : 5 // 最多显示项目
42     }) ;
43 }) ;            

 

2---,渲染并且完成时间绑定以及相关的业务逻辑,比如初始化时条目数量验证。

  

 1 tabProto.init = function(){
 2     if(this._isEmptyResult()){
 3         this._setContent("暂无任何模块!") ;
 4     }
 5     var that = this ;
 6     this.getElem().find(".title .adder")
 7     .text("+" + this.getOpts()["buttonText"])
 8     .on("click",function(){
 9         that.getElem().find(".console-panel").slideToggle(function(){
10             that._renderConsolePanel("0") ;
11         }) ;
12     }) ;
13     $.each(this.getOpts()["result"],function(i,item){
14         if(that._isDisplayMax(i + 1)){
15             that._saveOrUpdateStatus(item,"1") ;
16         }
17         else{
18             that._saveOrUpdateStatus(item,"2") ;
19         }
20         that._render(item) ;
21     }) ;
22     if(!that._isDisplayMax(this.getOpts()["result"].length)){
23         this.getElem().find(".title .more-mod").fadeIn(function(){
24             $(this).find(".tag").on("click",function(){
25                 var root = $(this).next() ;
26                 root.empty() ;
27                 $.each(that._getItemListByStatus("2"),function(i,data){
28                     $("<div></div>").text(data["text"])
29                     .on("click",function(){
30                         if(that._getItemListByStatus("1").length < that.getOpts()["displayMax"]){
31                             that.getElem().find(".title .items div").eq(data["index"]).fadeIn(function(){
32                                 that._saveOrUpdateStatus(data,"1") ;
33                             }) ;
34                         }
35                         else{
36                             alert("不能添加任何模块,目前已经是最大数量!") ;
37                         }
38                     })
39                     .appendTo(root) ;
40                 }) ;
41                 root.toggle() ;
42             }) ;
43             
44         });
45     }
46     this.getElem().find(".title .items div")
47     .eq(0)
48     .trigger("click") ; // 假定是必须有一项,否则插件意义就不大了!
49 } ;

 

3---,选项卡切换以及数据内容渲染操作。

  

1 tabProto._setCurrent = function(index){
2     var items = this.getElem().find(".title .items div").removeClass("active") ;
3     items.eq(index).addClass("active") ;
4     var contents = this.getElem().find(".content .c").hide() ;
5     contents.eq(index).show() ;
6 } ;    

 

1 item.on("click",function(){
2     that._setCurrent($(this).index()) ;
3     that._getContent(data["url"]).done(function(result){
4         that._setContent(result) ;
5     })
6     .fail(function(){
7         throw new Error("Net Error !") ;
8     });
9 })

 

 

1 tabProto._setContent = function(html){
2     this.getElem().find(".content").html(html) ;
3 } ;
4 tabProto._getContent = function(url){
5     return $.ajax({
6         url : url
7     }) ;
8 } ;

 

4---,核心的辅助数据操作方法,不涉及dom。

 1 /* update time 2015 1/26 15:36 */ 
 2 tabProto._isDisplayMax = function(size){
 3     var displayMax = this.getOpts()["displayMax"] || 5 ;
 4     return (size <= displayMax) ? true : false ;
 5 } ;
 6 tabProto._isEmptyResult = function(){
 7     if(!this.getOpts()["result"].length){
 8         return false ;
 9     }
10     return true ;
11 } ;
12 tabProto._saveOrUpdateStatus = function(item,status){
13     item["status"] = status ;
14 } ;
15 tabProto._getItemListByStatus = function(status){
16     var list = [] ;
17     var result = this.getOpts()["result"] ;
18     $.each(result,function(i,item){
19         if(status == item["status"]){
20             list.push(item) ;
21         }
22     }) ;
23     return list ;
24 } ;
25 tabProto._getStatusByIndex = function(index){
26     var status = null ;
27     var result = this.getOpts()["result"] ;
28     $.each(result,function(i,item){
29         if(index == item["index"]){
30             status = item["status"] ;
31         }
32     }) ;
33     return status ;
34 } ;

 

(三),完整代码以供学习,本代码已经过测试,包括目录结构以及相关的文件。

 1,html

 1 <body>
 2     <div class="dxj-ui-hd">
 3         大熊君{{bb}} - DXJ UI ------ Tab
 4     </div>
 5     <div class="dxj-ui-bd">
 6         <div id="tab">
 7             <div class="title">
 8                 <div class="adder">
 9                     + 添加学生信息
10                 </div>
11                 <div class="items">
12                     <!--<div><span class="del">X</span>欢迎页</div>
13                     <div><span class="del">X</span>用户管理</div>
14                     <div><span class="del">X</span>Bigbear</div>-->
15                 </div>
16                 <div class="more-mod">
17                     <div class="tag">更多模块</div>
18                     <div class="mods">
19                         
20                     </div>
21                 </div>
22             </div>
23             <div class="console-panel">
24             </div>
25             <div class="content">
26                 <!--<div class="c">
27                 
28                     <div class="input-content"><span>姓名:</span><input type="text" /></div>
29                     <div class="input-content"><span>备注:</span><textarea></textarea></div>
30                 
31                 </div>    <div class="input-content"><input type="button" value="保存" /></div>
32                 -->
33             </div>
34         </div>
35     </div>
36 </body>

 

2,css

  

  1 .dxj-ui-hd {
  2     padding:0px ;
  3     margin : 0 auto;
  4     margin-top:30px;
  5     width:780px;
  6     height:60px;
  7     line-height: 60px;
  8     background: #3385ff;
  9     color:#fff;
 10     font-family: "微软雅黑" ;
 11     font-size: 28px;
 12     text-align: center;
 13     font-weight:bold;
 14 }
 15 .dxj-ui-bd {
 16     padding:0px ;
 17     margin : 0 auto;
 18     width:778px;
 19     padding-top : 30px ;
 20     padding-bottom : 30px ;
 21     overflow: hidden;
 22     border:1px solid #3385ff;
 23 }
 24 .dxj-ui-bd #tab {
 25     padding:0px ;
 26     margin : 0 auto;
 27     width:720px;
 28     overflow: hidden;
 29     position:relative;
 30 }
 31 .dxj-ui-bd #tab .title {
 32     width:720px;
 33     overflow: hidden;
 34     border-bottom:2px solid #3385ff;
 35 }
 36 .dxj-ui-bd #tab .title .adder {
 37     width:160px;
 38     height:32px;
 39     line-height: 32px;
 40     background: #DC143C;
 41     color:#fff;
 42     font-family: "微软雅黑" ;
 43     font-size: 14px;
 44     text-align: center;
 45     font-weight:bold;
 46     float : left;
 47     cursor:pointer;
 48 }
 49 .dxj-ui-bd #tab .title .more-mod {
 50     overflow:hidden;
 51     border:1px solid #DC143C;
 52     width:70px;
 53     position:absolute;
 54     right:0;
 55     margin-right:6px;
 56     display:none;
 57 }
 58 .dxj-ui-bd #tab .title .more-mod .tag{
 59     height:32px;
 60     line-height:32px;
 61     width:70px;
 62     background: #DC143C;
 63     color:#fff;
 64     font-family: arial ;
 65     font-size: 12px;
 66     text-align: center;
 67     cursor:pointer;
 68 }
 69 .dxj-ui-bd #tab .title .more-mod .mods {
 70     overflow:hidden;
 71     width:70px;
 72     display:none;
 73 }
 74 .dxj-ui-bd #tab .title .more-mod .mods div {
 75     height:24px;
 76     line-height:24px;
 77     width:62px;
 78     font-family: arial ;
 79     font-size: 12px;
 80     cursor:pointer;
 81     padding-left:10px;
 82 }
 83 .dxj-ui-bd #tab .title .items {
 84     height:32px;
 85 
 86     width:480px;
 87     overflow: hidden;
 88     float : left;
 89 }
 90 .dxj-ui-bd #tab .title .items div {
 91     padding:0px;
 92     margin-left:10px;
 93     width:84px;
 94     height:32px;
 95     line-height: 32px;
 96     background: #3385ff;
 97     color:#fff;
 98     font-family: arial ;
 99     font-size: 12px;
100     text-align: center;
101     position:relative;
102     float : left;
103     cursor:pointer;
104 }
105 .dxj-ui-bd #tab .title .items div span.del {
106     width:16px;
107     height:16px;
108     line-height: 16px;
109     display:block;
110     background: #DC143C;
111     position:absolute;
112     right:0 ;
113     top:0;
114     cursor:pointer;
115 }
116 .dxj-ui-bd #tab .content {
117     width:716px;
118     padding-top:30px;
119     overflow: hidden;
120     border:2px solid #3385ff;
121     border-top:0px;
122     min-height:130px;
123     text-align:center;
124 }
125 .dxj-ui-bd #tab .content table {
126     margin : 0 auto ;
127 }
128 .dxj-ui-bd #tab .content div.c {
129     padding-top : 20px ;
130     padding-left:20px;
131     background:#eee;
132     height:140px;
133 }
134 .dxj-ui-bd #tab .content div.c .input-content {
135     margin-top : 10px ;
136     font-family: arial ;
137     font-size: 12px;
138 }
139 .dxj-ui-bd #tab .console-panel {
140     width:716px;
141     padding-top:20px;
142     padding-bottom:20px;
143     overflow: hidden;
144     border:2px solid #3385ff;
145     border-top:0px;
146     border-bottom:2px solid #3385ff;
147     background:#fff;
148     display:none;
149 }
150 
151 .active {
152     font-weight:bold ;
153 }

 

3,bigbear.js

    

(function($){var win = window ;var bb = win.bigbear = win.bigbear || {ui : {}} ;var ui = bb.ui = {} ;var Tab = function(elem,opts){this.elem = elem ;this.opts = opts ;} ;var tabProto = Tab.prototype ;/* update time 2015 1/26 15:36 */ tabProto._isDisplayMax = function(size){var displayMax = this.getOpts()["displayMax"] || 5 ;return (size <= displayMax) ? true : false ;} ;tabProto._isEmptyResult = function(){if(!this.getOpts()["result"].length){return false ;}return true ;} ;tabProto._saveOrUpdateStatus = function(item,status){item["status"] = status ;} ;tabProto._getItemListByStatus = function(status){var list = [] ;var result = this.getOpts()["result"] ;$.each(result,function(i,item){if(status == item["status"]){list.push(item) ;}}) ;return list ;} ;tabProto._getStatusByIndex = function(index){var status = null ;var result = this.getOpts()["result"] ;$.each(result,function(i,item){if(index == item["index"]){status = item["status"] ;}}) ;return status ;} ;tabProto._renderConsolePanel = function(status){var that = this ;var root = that.getElem().find(".console-panel") ;this._resetConsolePanel() ;$.each(that._getItemListByStatus(status),function(i,item){var elem = $("<div style='float:left';></div>").appendTo(root) ;$("<input type='radio' name='addmod' />").data("item",item).appendTo(elem) ;$("<span></span>").text(item["text"]).appendTo(elem) ;}) ;if(root.find("div").size()){$("<input type='button' value='添加模块' style='margin-left:20px'/>").on("click",function(){var data = root.find("input[type=radio]:checked").data("item") ;if(that._getItemListByStatus("1").length < that.getOpts()["displayMax"]){that.getElem().find(".title .items div").eq(data["index"]).fadeIn(function(){that._saveOrUpdateStatus(data,"1") ;}).trigger("click") ;}else{that._saveOrUpdateStatus(data,"2") ;}that.getElem().find(".title .adder").trigger("click") ;}).appendTo(root) ;}else{root.text("暂无任何可添加的项目!") ;}} ;/* update time 2015 1/26 15:36 */ 	tabProto._setCurrent = function(index){var items = this.getElem().find(".title .items div").removeClass("active") ;items.eq(index).addClass("active") ;var contents = this.getElem().find(".content .c").hide() ;contents.eq(index).show() ;} ;	tabProto.getElem = function(){return this.elem ;} ;tabProto.getOpts = function(){return this.opts ;} ;tabProto._resetContent = function(){this.getElem().find(".content").html("") ;} ;tabProto._setContent = function(html){this.getElem().find(".content").html(html) ;} ;tabProto._getContent = function(url){return $.ajax({url : url}) ;} ;tabProto._deleteItem = function(elem){var that = this ;this.getElem().find(".title .items div").eq(elem.index()).fadeOut(function(){that._resetContent() ;that._saveOrUpdateStatus(elem.data("item"),"0") ;that._triggerItem(elem.index() + 1) ;}) ;} ;tabProto._triggerItem = function(next){var nextStatus = this._getStatusByIndex(next) ;var items = this.getElem().find(".title .items div") ;next = items.eq(next) ;if(next.size() && "1" == nextStatus){ //后继dom节点存在next.trigger("click") ;}else{items.eq(0).trigger("click") ;}} ;tabProto._resetConsolePanel = function(){this.getElem().find(".console-panel").empty() ;} ;tabProto.init = function(){if(this._isEmptyResult()){this._setContent("暂无任何模块!") ;}var that = this ;this.getElem().find(".title .adder").text("+" + this.getOpts()["buttonText"]).on("click",function(){that.getElem().find(".console-panel").slideToggle(function(){that._renderConsolePanel("0") ;}) ;}) ;$.each(this.getOpts()["result"],function(i,item){if(that._isDisplayMax(i + 1)){that._saveOrUpdateStatus(item,"1") ;}else{that._saveOrUpdateStatus(item,"2") ;}that._render(item) ;}) ;if(!that._isDisplayMax(this.getOpts()["result"].length)){this.getElem().find(".title .more-mod").fadeIn(function(){$(this).find(".tag").on("click",function(){var root = $(this).next() ;root.empty() ;$.each(that._getItemListByStatus("2"),function(i,data){$("<div></div>").text(data["text"]).on("click",function(){if(that._getItemListByStatus("1").length < that.getOpts()["displayMax"]){that.getElem().find(".title .items div").eq(data["index"]).fadeIn(function(){that._saveOrUpdateStatus(data,"1") ;}) ;}else{alert("不能添加任何模块,目前已经是最大数量!") ;}}).appendTo(root) ;}) ;root.toggle() ;}) ;});}this.getElem().find(".title .items div").eq(0).trigger("click") ; // 假定是必须有一项,否则插件意义就不大了!} ;tabProto._render = function(data){var that = this ;var item = $("<div></div>").text(data["text"]).appendTo(this.getElem().find(".title .items")) ;data["index"] = item.index() ;item.on("click",function(){that._setCurrent($(this).index()) ;that._getContent(data["url"]).done(function(result){that._setContent(result) ;}).fail(function(){throw new Error("Net Error !") ;});}).data("item",data) ;if("2" == data["status"]){item.hide() ;}if("1" == data["showClose"]){$("<span class='del'>X</span>").on("click",function(){if(win.confirm("是否删除此项?")){that._deleteItem(item) ;return false ; // 阻止冒泡}}).appendTo(item) ;} } ;ui.createTab = function(elem,opts){var tab = new Tab(elem,opts) ;tab.init() ;return tab ;} ;		
})(jQuery) ;

  

(四),最后总结

  (1),面向对象的思考方式合理分析功能需求。

  (2),以类的方式来组织我们的插件逻辑。

  (3),不断重构上面的实例,如何进行合理的重构那?不要设计过度,要游刃有余,推荐的方式是过程化设计与面向对象思想设计相结合。

   

 

                   哈哈哈,本篇结束,未完待续,希望和大家多多交流够沟通,共同进步。。。。。。呼呼呼……(*^__^*)                

转载于:https://www.cnblogs.com/bigbearbb/p/4251160.html

这篇关于大熊君JavaScript插件化开发------(实战篇之DXJ UI ------ Tab功能扩展完结版)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/237207

相关文章

基于Python开发电脑定时关机工具

《基于Python开发电脑定时关机工具》这篇文章主要为大家详细介绍了如何基于Python开发一个电脑定时关机工具,文中的示例代码讲解详细,感兴趣的小伙伴可以跟随小编一起学习一下... 目录1. 简介2. 运行效果3. 相关源码1. 简介这个程序就像一个“忠实的管家”,帮你按时关掉电脑,而且全程不需要你多做

Go语言实现将中文转化为拼音功能

《Go语言实现将中文转化为拼音功能》这篇文章主要为大家详细介绍了Go语言中如何实现将中文转化为拼音功能,文中的示例代码讲解详细,感兴趣的小伙伴可以跟随小编一起学习一下... 有这么一个需求:新用户入职 创建一系列账号比较麻烦,打算通过接口传入姓名进行初始化。想把姓名转化成拼音。因为有些账号即需要中文也需要英

基于WinForm+Halcon实现图像缩放与交互功能

《基于WinForm+Halcon实现图像缩放与交互功能》本文主要讲述在WinForm中结合Halcon实现图像缩放、平移及实时显示灰度值等交互功能,包括初始化窗口的不同方式,以及通过特定事件添加相应... 目录前言初始化窗口添加图像缩放功能添加图像平移功能添加实时显示灰度值功能示例代码总结最后前言本文将

Java中的Opencv简介与开发环境部署方法

《Java中的Opencv简介与开发环境部署方法》OpenCV是一个开源的计算机视觉和图像处理库,提供了丰富的图像处理算法和工具,它支持多种图像处理和计算机视觉算法,可以用于物体识别与跟踪、图像分割与... 目录1.Opencv简介Opencv的应用2.Java使用OpenCV进行图像操作opencv安装j

vue解决子组件样式覆盖问题scoped deep

《vue解决子组件样式覆盖问题scopeddeep》文章主要介绍了在Vue项目中处理全局样式和局部样式的方法,包括使用scoped属性和深度选择器(/deep/)来覆盖子组件的样式,作者建议所有组件... 目录前言scoped分析deep分析使用总结所有组件必须加scoped父组件覆盖子组件使用deep前言

Python中的可视化设计与UI界面实现

《Python中的可视化设计与UI界面实现》本文介绍了如何使用Python创建用户界面(UI),包括使用Tkinter、PyQt、Kivy等库进行基本窗口、动态图表和动画效果的实现,通过示例代码,展示... 目录从像素到界面:python带你玩转UI设计示例:使用Tkinter创建一个简单的窗口绘图魔法:用

VUE动态绑定class类的三种常用方式及适用场景详解

《VUE动态绑定class类的三种常用方式及适用场景详解》文章介绍了在实际开发中动态绑定class的三种常见情况及其解决方案,包括根据不同的返回值渲染不同的class样式、给模块添加基础样式以及根据设... 目录前言1.动态选择class样式(对象添加:情景一)2.动态添加一个class样式(字符串添加:情

使用Python实现批量访问URL并解析XML响应功能

《使用Python实现批量访问URL并解析XML响应功能》在现代Web开发和数据抓取中,批量访问URL并解析响应内容是一个常见的需求,本文将详细介绍如何使用Python实现批量访问URL并解析XML响... 目录引言1. 背景与需求2. 工具方法实现2.1 单URL访问与解析代码实现代码说明2.2 示例调用

基于Qt开发一个简单的OFD阅读器

《基于Qt开发一个简单的OFD阅读器》这篇文章主要为大家详细介绍了如何使用Qt框架开发一个功能强大且性能优异的OFD阅读器,文中的示例代码讲解详细,有需要的小伙伴可以参考一下... 目录摘要引言一、OFD文件格式解析二、文档结构解析三、页面渲染四、用户交互五、性能优化六、示例代码七、未来发展方向八、结论摘要

element-ui下拉输入框+resetFields无法回显的问题解决

《element-ui下拉输入框+resetFields无法回显的问题解决》本文主要介绍了在使用ElementUI的下拉输入框时,点击重置按钮后输入框无法回显数据的问题,具有一定的参考价值,感兴趣的... 目录描述原因问题重现解决方案方法一方法二总结描述第一次进入页面,不做任何操作,点击重置按钮,再进行下