JavaScript 多级联动select

能够根据自定义的菜单数据和select,自动设置联级的下拉菜单,可定义默认值。

效果:
<style type="text/css"> .sel select{ width:100px;} </style> <script type="text/javascript"> var $$ = function (id) { return "string" == typeof id ? document.getElementById(id) : id; }; function addEventHandler(oTarget, sEventType, fnHandler) { if (oTarget.addEventListener) { oTarget.addEventListener(sEventType, fnHandler, false); } else if (oTarget.attachEvent) { oTarget.attachEvent("on" + sEventType, fnHandler); } else { oTarget["on" + sEventType] = fnHandler; } }; function Each(arrList, fun){ for (var i = 0, len = arrList.length; i < len; i++) { fun(arrList[i], i); } }; function GetOption(val, txt) { var op = document.createElement("OPTION"); op.value = val; op.innerHTML = txt; return op; }; var Class = { create: function() { return function() { this.initialize.apply(this, arguments); } } } Object.extend = function(destination, source) { for (var property in source) { destination[property] = source[property]; } return destination; } var CascadeSelect = Class.create(); CascadeSelect.prototype = { //select集合,菜单对象 initialize: function(arrSelects, arrMenu, options) { if(arrSelects.length <= 0 || arrMenu.lenght <= 0) return;//菜单对象 var oThis = this; this.Selects = [];//select集合 this.Menu = arrMenu;//菜单对象 this.SetOptions(options); this.Default = this.options.Default || []; this.ShowEmpty = !!this.options.ShowEmpty; this.EmptyText = this.options.EmptyText.toString(); //设置Selects集合和change事件 Each(arrSelects, function(o, i){ addEventHandler((oThis.Selects[i] = $$(o)), "change", function(){ oThis.Set(i); }); }); this.ReSet(); }, //设置默认属性 SetOptions: function(options) { this.options = {//默认值 Default: [],//默认值(按顺序) ShowEmpty: false,//是否显示空值(位于第一个) EmptyText: "请选择"//空值显示文本(ShowEmpty为true时有效) }; Object.extend(this.options, options || {}); }, //初始化select ReSet: function() { this.SetSelect(this.Selects[0], this.Menu, this.Default.shift()); this.Set(0); }, //全部select设置 Set: function(index) { var menu = this.Menu //第一个select不需要处理所以从1开始 for(var i=1, len = this.Selects.length; i < len; i++){ if(menu.length > 0){ //获取菜单 var value = this.Selects[i-1].value; if(value!=""){ Each(menu, function(o){ if(o.val == value){ menu = o.menu || []; } }); } else { menu = []; } //设置菜单 if(i > index){ this.SetSelect(this.Selects[i], menu, this.Default.shift()); } } else { //没有数据 this.SetSelect(this.Selects[i], [], ""); } } //清空默认值 this.Default.length = 0; }, //select设置 SetSelect: function(oSel, menu, value) { oSel.options.length = 0; oSel.disabled = false; if(this.ShowEmpty){ oSel.appendChild(GetOption("", this.EmptyText)); } if(menu.length <= 0){ oSel.disabled = true; return; } Each(menu, function(o){ var op = GetOption(o.val, o.txt ? o.txt : o.val); op.selected = (value == op.value); oSel.appendChild(op); }); }, //添加菜单 Add: function(menu) { this.Menu[this.Menu.length] = menu; this.ReSet(); }, //删除菜单 Delete: function(index) { if(index < 0 || index >= this.Menu.length) return; for(var i = index, len = this.Menu.length - 1; i < len; i++){ this.Menu[i] = this.Menu[i + 1]; } this.Menu.pop() this.ReSet(); } }; </script>

<script type="text/javascript"> var menu = [ {'val': '1', 'txt': 'value'}, {'val': '2 ->', 'menu': [ {'val': '2_1'}, {'val': '2_2'} ]}, {'val': '3 ->', 'menu': [ {'val': '3_1 ->', 'menu': [ {'val': '3_1_1'}, {'val': '3_1_2'} ]}, {'val': '3_2'} ]}, {'val': '4 ->', 'menu': [ {'val': '4_1 ->', 'menu': [ {'val': '4_1_1 ->', 'menu': [ {'val': '4_1_1_1'} ]} ]} ]} ]; var sel=["sel1", "sel2", "sel3", "sel4", "sel5"]; var val=["3 ->", "3_1 ->", "3_1_2"]; var cs = new CascadeSelect(sel, menu, { Default: val }); $$("btnA").οnclick=function(){cs.ShowEmpty=!cs.ShowEmpty;} $$("btnB").οnclick=function(){ cs.Add( {'val': '5 ->', 'menu': [ {'val': '5_1 ->', 'menu': [ {'val': '5_1_1 ->', 'menu': [ {'val': '5_1_1_1 ->', 'menu': [ {'val': '5_1_1_1_1'} ]} ]} ]} ]} ) } $$("btnC").οnclick=function(){ cs.Delete(3) }</script>
其中参数1是菜单结构:
菜单对象
<!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />-->var menu = [
    {
'val''1''txt''value'},
    {
'val''2 ->''menu': [
        {
'val''2_1'},
        {
'val''2_2'}
    ]},
    {
'val''3 ->''menu': [
        {
'val''3_1 ->''menu': [
            {
'val''3_1_1'},
            {
'val''3_1_2'}
        ]},
        {
'val''3_2'}
    ]},
    {
'val''4 ->''menu': [
        {
'val''4_1 ->''menu': [
            {
'val''4_1_1 ->''menu': [
                {
'val''4_1_1_1'}
            ]}
        ]}
    ]}
];

参数2是select的id集合(按顺序):
var  sel = [ " sel1 " , " sel2 " , " sel3 " , " sel4 " , " sel5 " ]

可设置默认值(按顺序):
var  val = [ " 3 -> " " 3_1 -> " " 3_1_2 " ];

源码:
<! DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd" >
< html  xmlns ="http://www.w3.org/1999/xhtml" >
< head >
< meta  http-equiv ="Content-Type"  content ="text/html; charset=gb2312"   />
< title > JavaScript 自定义多级联动下拉菜单 </ title >
< script  type ="text/javascript" >
var  $  =   function  (id) {
    
return   " string "   ==   typeof  id  ?  document.getElementById(id) : id;
};

function  addEventHandler(oTarget, sEventType, fnHandler) {
    
if  (oTarget.addEventListener) {
        oTarget.addEventListener(sEventType, fnHandler, 
false );
    } 
else   if  (oTarget.attachEvent) {
        oTarget.attachEvent(
" on "   +  sEventType, fnHandler);
    } 
else  {
        oTarget[
" on "   +  sEventType]  =  fnHandler;
    }
};

function  Each(arrList, fun){
    
for  ( var  i  =   0 , len  =  arrList.length; i  <  len; i ++ ) { fun(arrList[i], i); }
};

function  GetOption(val, txt) {
    
var  op  =  document.createElement( " OPTION " );
    op.value 
=  val; op.innerHTML  =  txt;
    
return  op;
};

var  Class  =  {
  create: 
function () {
    
return   function () {
      
this .initialize.apply( this , arguments);
    }
  }
}

Object.extend 
=   function (destination, source) {
    
for  ( var  property  in  source) {
        destination[property] 
=  source[property];
    }
    
return  destination;
}


var  CascadeSelect  =  Class.create();
CascadeSelect.prototype 
=  {
  
// select集合,菜单对象
  initialize:  function (arrSelects, arrMenu, options) {
    
if (arrSelects.length  <=   0   ||  arrMenu.lenght  <=   0 return ; // 菜单对象
    
    
var  oThis  =   this ;
    
    
this .Selects  =  []; // select集合
     this .Menu  =  arrMenu; // 菜单对象
    
    
this .SetOptions(options);
    
    
this .Default  =   this .options.Default  ||  [];
    
    
this .ShowEmpty  =   !! this .options.ShowEmpty;
    
this .EmptyText  =   this .options.EmptyText.toString();
    
    
// 设置Selects集合和change事件
    Each(arrSelects,  function (o, i){
        addEventHandler((oThis.Selects[i] 
=  $(o)),  " change " function (){ oThis.Set(i); });
    });
    
    
this .ReSet();
  },
  
// 设置默认属性
  SetOptions:  function (options) {
    
this .options  =  { // 默认值
        Default:    [], // 默认值(按顺序)
        ShowEmpty:     false , // 是否显示空值(位于第一个)
        EmptyText:     " 请选择 " // 空值显示文本(ShowEmpty为true时有效)
    };
    Object.extend(
this .options, options  ||  {});
  },
  
// 初始化select
  ReSet:  function () {
  
    
this .SetSelect( this .Selects[ 0 ],  this .Menu,  this .Default.shift());
    
this .Set( 0 );
  },
  
// 全部select设置
  Set:  function (index) {
    
var  menu  =   this .Menu
    
    
// 第一个select不需要处理所以从1开始
     for ( var  i = 1 , len  =   this .Selects.length; i  <  len; i ++ ){
        
if (menu.length  >   0 ){
            
// 获取菜单
             var  value  =   this .Selects[i - 1 ].value;
            
if (value != "" ){
                Each(menu, 
function (o){  if (o.val  ==  value){ menu  =  o.menu  ||  []; } });
            } 
else  { menu  =  []; }
            
            
// 设置菜单
             if (i  >  index){  this .SetSelect( this .Selects[i], menu,  this .Default.shift()); }
        } 
else  {
            
// 没有数据
             this .SetSelect( this .Selects[i], [],  "" );
        }
    }
    
// 清空默认值
     this .Default.length  =   0 ;
  },
  
// select设置
  SetSelect:  function (oSel, menu, value) {
    oSel.options.length 
=   0 ; oSel.disabled  =   false ;
    
if ( this .ShowEmpty){ oSel.appendChild(GetOption( "" this .EmptyText)); }
    
if (menu.length  <=   0 ){ oSel.disabled  =   true return ; }
    
    Each(menu, 
function (o){
        
var  op  =  GetOption(o.val, o.txt  ?  o.txt : o.val); op.selected  =  (value  ==  op.value);
        oSel.appendChild(op);
    });    
  },
  
// 添加菜单
  Add:  function (menu) {
    
this .Menu[ this .Menu.length]  =  menu;
    
this .ReSet();
  },
  
// 删除菜单
  Delete:  function (index) {
    
if (index  <   0   ||  index  >=   this .Menu.length)  return ;
    
for ( var  i  =  index, len  =   this .Menu.length  -   1 ; i  <  len; i ++ ){  this .Menu[i]  =   this .Menu[i  +   1 ]; }
    
this .Menu.pop()
    
this .ReSet();
  }
};


window.onload
= function (){
    
    
var  menu  =  [
        {
' val ' ' 1 ' ' txt ' ' value ' },
        {
' val ' ' 2 -> ' ' menu ' : [
            {
' val ' ' 2_1 ' },
            {
' val ' ' 2_2 ' }
        ]},
        {
' val ' ' 3 -> ' ' menu ' : [
            {
' val ' ' 3_1 -> ' ' menu ' : [
                {
' val ' ' 3_1_1 ' },
                {
' val ' ' 3_1_2 ' }
            ]},
            {
' val ' ' 3_2 ' }
        ]},
        {
' val ' ' 4 -> ' ' menu ' : [
            {
' val ' ' 4_1 -> ' ' menu ' : [
                {
' val ' ' 4_1_1 -> ' ' menu ' : [
                    {
' val ' ' 4_1_1_1 ' }
                ]}
            ]}
        ]}
    ];
    
    
var  sel = [ " sel1 " " sel2 " " sel3 " " sel4 " " sel5 " ];
    
    
var  val = [ " 3 -> " " 3_1 -> " " 3_1_2 " ];
    
    
var  cs  =   new  CascadeSelect(sel, menu, { Default: val });
    
    $(
" btnA " ).onclick = function (){cs.ShowEmpty =! cs.ShowEmpty;}
    
    $(
" btnB " ).onclick = function (){
        cs.Add(
            {
' val ' ' 5 -> ' ' menu '
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: 在 layui 中,可以通过使用下拉框的 onchange 事件来实现级联效果。具体实现步骤如下: 1. 定义省份、城市、区县的下拉框: ```html <select name="province" lay-filter="province"> <option value="">请选择省份</option> <option value="1">湖南省</option> <option value="2">广东省</option> ... </select> <select name="city" lay-filter="city"> <option value="">请选择城市</option> </select> <select name="district" lay-filter="district"> <option value="">请选择区县</option> </select> ``` 2. 在 JavaScript 中编写下拉框的 onchange 事件: ```javascript <script> layui.use(['form'], function(){ var form = layui.form; // 监听省份下拉框的选择事件 form.on('select(province)', function(data){ // 获取当前选择的省份 var provinceId = data.value; // 清空城市下拉框的选项 $("select[name='city']").html("<option value=''>请选择城市</option>"); // 清空区县下拉框的选项 $("select[name='district']").html("<option value=''>请选择区县</option>"); // 如果省份不为空,则通过 Ajax 请求获取对应的城市列表 if(provinceId != ''){ $.get("/api/city?provinceId="+provinceId,function(data){ // 循环添加城市选项 for(var i=0;i<data.length;i++){ $("select[name='city']").append("<option value='"+data[i].cityId+"'>"+data[i].cityName+"</option>"); } // 重新渲染城市下拉框 form.render('select'); }); } }); // 监听城市下拉框的选择事件 form.on('select(city)', function(data){ // 获取当前选择的城市 var cityId = data.value; // 清空区县下拉框的选项 $("select[name='district']").html("<option value=''>请选择区县</option>"); // 如果城市不为空,则通过 Ajax 请求获取对应的区县列表 if(cityId != ''){ $.get("/api/district?cityId="+cityId,function(data){ // 循环添加区县选项 for(var i=0;i<data.length;i++){ $("select[name='district']").append("<option value='"+data[i].districtId+"'>"+data[i].districtName+"</option>"); } // 重新渲染区县下拉框 form.render('select'); }); } }); }); </script> ``` 3. 在服务器端编写对应的 API 接口,用于根据省份和城市获取对应的城市和区县列表。 以上就是 layui 实现级联的简单示例。 ### 回答2: layui是一款基于jQuery的前端UI框架,其中的select级联组件可以实现多级下拉菜单之间的关联。使用layui的select级联组件,可以通过简单的代码实现省市区三级联或其他自定义的多级联效果。 首先,我们需要引入layui的资源文件,并初始化一个select实例。然后,设置select的外观样式和数据源。 接下来,我们需要定义各级选项的数据源。可以使用数组或JSON对象来表示。第一级的选项数据可以直接写在html中,而后续级的选项数据可以使用layui的form组件的on()方法来监听前一级的选择事件,并根据选择的值态加载后续级的选项数据。 在监听事件的回调函数中,我们可以根据前一级的选择值来态生成后续级的选项数据,并使用layui的select组件的render()方法重新渲染后续级的select实例,实现级联的效果。 例如,如果要实现省市区三级联,可以定义一个省级的select实例,并设置省级选项数据。接着,监听省级select实例的选择事件,在回调函数中根据选择的省份态生成市级的选项数据,并使用layui的select组件的render()方法重新渲染市级的select实例。然后,再监听市级select实例的选择事件,在回调函数中态生成区级的选项数据,并重新渲染区级的select实例。 通过这样的方式,就可以实现layui的select级联的效果。 总之,layui的select级联组件可以方便地实现多级下拉菜单之间的关联,通过监听选择事件和态生成选项数据来实现联动效果。使用layui的select级联组件可以提升用户体验,增强网站的交互性。 ### 回答3: Layui是一个快速构建前端界面的模块化框架,它提供了多种常用的UI组件。其中的select级联是指在一个表单中的多个下拉列表之间建立关联,选择一个下拉列表的选项会影响另一个下拉列表的选项内容。 在Layui中,实现select级联有以下几个步骤: 1. 在HTML中定义对应的下拉列表元素,给每个下拉列表元素设置一个唯一的id。 2. 在JavaScript中使用Layui的form模块,使用form.on方法监听每个下拉列表的选择事件。 3. 在监听事件中获取当前选择的选项值,并根据该值设置下一个下拉列表的选项。 下面以一个三级联为例进行说明: HTML代码: ```html <select id="province"> <option value="">请选择省份</option> <option value="广东省">广东省</option> <option value="江苏省">江苏省</option> </select> <select id="city"> <option value="">请选择城市</option> </select> <select id="district"> <option value="">请选择区县</option> </select> ``` JavaScript代码: ```javascript layui.use('form', function () { var form = layui.form; // 监听省份下拉列表的选择事件 form.on('select(province)', function (data) { var province = data.value; if (province === '广东省') { // 态设置城市下拉列表的选项 $('#city').html('<option value="广州市">广州市</option><option value="深圳市">深圳市</option>'); } else if (province === '江苏省') { // 态设置城市下拉列表的选项 $('#city').html('<option value="南京市">南京市</option><option value="苏州市">苏州市</option>'); } else { // 清空城市下拉列表的选项 $('#city').html('<option value="">请选择城市</option>'); } // 清空区县下拉列表的选项 $('#district').html('<option value="">请选择区县</option>'); // 重新渲染下拉列表 form.render('select'); }); // 监听城市下拉列表的选择事件 form.on('select(city)', function (data) { var city = data.value; if (city === '广州市') { // 态设置区县下拉列表的选项 $('#district').html('<option value="天河区">天河区</option><option value="海珠区">海珠区</option>'); } else if (city === '深圳市') { // 态设置区县下拉列表的选项 $('#district').html('<option value="福田区">福田区</option><option value="罗湖区">罗湖区</option>'); } else if (city === '南京市') { // 态设置区县下拉列表的选项 $('#district').html('<option value="玄武区">玄武区</option><option value="鼓楼区">鼓楼区</option>'); } else if (city === '苏州市') { // 态设置区县下拉列表的选项 $('#district').html('<option value="姑苏区">姑苏区</option><option value="吴中区">吴中区</option>'); } else { // 清空区县下拉列表的选项 $('#district').html('<option value="">请选择区县</option>'); } // 重新渲染下拉列表 form.render('select'); }); }); ``` 以上代码实现了一个三级联的效果,根据选择的省份和城市态改变区县下拉列表的选项内容。在监听选择事件时,根据选择的选项值设置下一个下拉列表的选项,并通过form.render('select')重新渲染下拉列表,使其生效。 注意,在使用Layui的select级联前,需要先引入Layui的相关资源文件,如layui.js和layui.css
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值