JS省市區聯動

龍恩0707發表於2014-09-27

JS省市區使用文件

  一:伺服器返回JSON格式要求如下網址裡面data的格式:(拿KISSY元件data格式來做的)

        http://gallery.kissyui.com/cityselector/doc/linkage-data.js 

   二:使用時,頁面head部分需要引入jquery和省市區JS,依賴於HTML結構如下:

        <select  id="prov4" data-code="220000"></select>

        <select  id="city4" data-code="220300"></select>

        <select  id="area4" data-code="220322"></select>

        屬性說明:

             id:下拉框dom節點(頁面上是唯一的),用於js初始化的鉤子。

            data-code: 初始化頁面時可以根據省市區的編碼來指定那個省份,市及區來顯示。比如我想指定 "吉林省 長春市 朝陽區" 頁面預設顯示的話,我們可以在HTML結構上加相對應的data-code編碼來指定,比如如下:

            <select class="prov" id="prov4" data-code ="220000"></select>
            <select class="city" id="city4" data-code ="220100"></select>
            <select class="dist" id="area4" data-code ="220104"></select>

          頁面一開啟的時候如下顯示:

         

   三:省市區JS初始化的方法如下:

               var selectVal = new CitySelect({

                         data   : data,

                         provId : "#prov4",

                         cityId : '#city4',

                         areaId : '#area4'

                  });

       屬性說明如下:

           data: data配置項是指 後臺返回的json資料的儲存的全域性變數。

           provId 指省份下拉框select的id。

           cityId  指城市下拉框select的id。

           areaId  指區下拉框select的id。

         省市區id傳參方式:都是以 #XXX的.

省市區基本的配置項如下:

            data:                 指後臺返回的JSON資料。

            provId:            省份下拉框select的id。

            cityId:             指城市下拉框select的id。

            areaId:              指區下拉框select的id。

            isSelect:            預設為true 選擇第一項 如果頁面有指定省市區項時,就顯示指定項。如果false,就選中 "請選擇"  

            provCallBack:    省份下拉框渲染完成後的回撥函式。

            cityCallBack:    市下拉框渲染完成後的回撥函式。

            areaCallBack:   區下拉框渲染完成後的回撥函式。

demo演示:

    一:預設的HTML結構如下: 

         <select class="prov" id="prov4"></select>
         <select class="city" id="city4"></select>
         <select class="dist" id="area4"></select>

   JS程式碼初始化的方式如下:      

      var selectVal = new CitySelect({
           data : data,
           provId : "#prov4",
           cityId : '#city4',
           areaId : '#area4'
      });

     開啟頁面後,頁面顯示如下:

     

     1. 可以看到,頁面一開啟的時候 預設顯示第一項 北京,我們也可以根據 省 市 區 切換其他省份去,可以看到上面的gif圖時,下面的select中的屬性data-code也跟著變化,如果省份切換到請選擇下拉框時候,那麼省 市 區中的data-code變為-1,且市,區不可選擇,只能是 請選擇下拉框。

     2. 當有省份時候,我切換市 到 "請選擇"項時候 那麼區也變為請選擇 相應的 市和區 select中的data-code 值變為-1。其中data-code 就是form表單提交時候 需要的。也就是說 某某省份下的所有市和所有區。

     3. 當同時有省,市的時候,我區也可以change,那麼當選擇其他的區的時候 data-code也同時變化,當切換到請選擇的時候 那麼value為-1,也就是說是 某某省 某某市下面的所有區。 

   二: 第二種就是假如頁面一初始化的時候我想指定某某省 某某市 某某區的時候,要如何編寫HTML結構呢,比如像下面的圖上一樣。

          

         我們可以在select框加上data-code屬性來指定,如下:

         

        注意:如果我指定了省份是:浙江省,市:不是浙江省裡面的市,那麼選中的市是浙江省的預設的第一個市,同理 區也一樣。

   三: 第三種初始化是:通過配置項 isSelect 來配置的,預設此配置項為true,如果沒有指定省市區的話,那麼預設選種第一項,如果有指定省市區的話,那麼顯示指定的省市區。如果 isSelect 配置項為false的話,那麼預設顯示是 請選擇下拉框。可以看下程式碼如下判斷!

        

         我們也可以看看gif圖顯示的。

         

        如上gif圖所示:預設顯示都是 "請選擇"下拉框,data-code都為-1,當選擇 某某省時候 data-code值變化,但是相對應的 "市" 和 "區" 還是請選擇下拉框,同理當選中某項市的時候,select中的屬性data-code也相應的變化,但是區下拉框還是"請選擇"下拉框。當選擇區某項的時候 data-code也相應的變化。

       JS初始化方式如下,只需要增加一個配置項 isSelect:false即可,如下:

       var selectVa2 = new CitySelect({
             data : data,
             provId : "#prov5",
             cityId : '#city5',
             areaId : '#area5',
             isSelect: false
       });

下面是所有的HTML程式碼如下

<!doctype html>
<html lang="en">
 <head>
  <meta charset="UTF-8">
  <script type="text/javascript" src="js/jquery-1.4.4.min.js"></script>
  <script src="js/city2.js"></script>
  <script type="text/javascript" src="js/citySelect2.js"></script>
  <title>Document</title>
 </head>
 <body>

    <div id="city_4">
          <select class="prov" id="prov4" data-code ="220000"></select> 
        <select class="city" id="city4" data-code ="220100"></select>
        <select class="dist" id="area4" data-code ="220104"></select>
    </div>

    <div id="city_5">
          <select class="prov" id="prov5">
            
        </select> 
        <select class="city" id="city5"></select>
        <select class="dist" id="area5"></select>
    </div>
    <script>
            
            var selectVal = new CitySelect({
                data   : data,
                provId : "#prov4",
                cityId : '#city4',
                areaId : '#area4'
            });
            
                
            var selectVa2 = new CitySelect({
                data   : data,
                provId : "#prov5",
                cityId : '#city5',
                areaId : '#area5',
                isSelect: false
            });
            
    </script>
 </body>
</html>
View Code

javascript程式碼如下:

/**
 * Jquery省市區聯動程式碼重構
 * @version 0.0.2
 */

 function CitySelect(options) {
    this.config = {
         data             :      '',             // 資料
         provId           :      '',             // 省下拉框id容器 格式是 #XXX
         cityId           :      '',             // 市下拉框id容器 格式是 #XXX
         areaId           :      '',             // 區下拉框id容器 格式是 #XXX
         isSelect         :      true,           // 預設為true 選擇第一項 如果頁面有指定省市區項時,就顯示指定項。
                                                 // 如果false,就選中 "請選擇"
         provCallBack     :      null,           // 省份渲染完成後回撥
         cityCallBack     :      null,           // 市渲染完成後的回撥
         areaCallBack     :      null            // 區渲染完成後的回撥
    };
    this.config = $.extend(this.config, options || {});
    this.init();
 }

 CitySelect.prototype = {

    constructor: CitySelect,
    
    /*
     * 初始化方法init
     */
    init: function() {
        var self = this,
            _config = self.config;

        if(!/^#/.test(_config.provId)) {
            alert("省份ID傳的不正確,格式是 #XXX");
            return;
        }
        if(!/^#/.test(_config.cityId)) {
            alert("城市ID傳的不正確,格式是 #XXX");
            return;
        }
        if(!/^#/.test(_config.cityId)) {
            alert("區ID傳的不正確,格式是 #XXX");
            return;
        }
        this.provCode = $(_config.provId).attr("data-code");
        this.cityCode = $(_config.cityId).attr("data-code");
        this.areaCode = $(_config.areaId).attr("data-code");
        
        // 使省市區id (#XX --> XX)
        this.provid =  _config.provId.replace(/^#/g,'');
        this.cityid = _config.cityId.replace(/^#/g,'');
        this.areaid = _config.areaId.replace(/^#/g,'');

        // 渲染省份
        self._provFunc();

        //渲染省對應的市
        self._cityFunc();
        
        // 渲染省市 對應的區
        self._areaFunc();
        
        // 如果省份的值是-1的話 那麼設定省市區select都為-1
        var provFirstOpt = $(_config.provId).val();
        if(provFirstOpt == -1) {
            $(_config.provId).attr("data-code","-1");
            $(_config.cityId).attr("data-code","-1");
            $(_config.areaId).attr("data-code","-1");
        }
        // change事件 省切換 自動切換市 and 區 
        $(_config.provId).change(function(e){
            self._cityFunc();
            self._areaFunc();
        });

        // 市 change事件 自動切換區
        $(_config.cityId).change(function(e){
            self._areaFunc();
        });
        // 區change事件 
        $(_config.areaId).change(function(){
            $(_config.areaId).attr("data-code",$(this).val());
        });
    },
    /*
     * 渲染省資料
     * @method _provFunc {private}
     */
    _provFunc: function(){
        var self = this,
            _config = self.config;

        var elemHtml = '';
        elemHtml+= '<option value="-1" data-name="請選擇" selected>請選擇</option>';

        $(_config.data).each(function(i,curItem){
            elemHtml += "<option data-name='"+curItem[1]+"' value='"+curItem[0]+"'>"+curItem[1]+"</option>";
        });
        $(_config.provId).html(elemHtml);
        
        if(_config.isSelect) {
            $($(_config.provId + " option")[1]).attr("selected",'true');
            if(this.provCode) {
                self._setSelectCode(_config.provId,this.provCode);
            }
        }
        
        _config.provCallBack && $.isFunction(_config.provCallBack) && _config.provCallBack();
    },
    /*
     * 渲染省對應的市資料
     * @method _cityFunc {private}
     */
    _cityFunc: function(){
        var self = this,
            _config = self.config;

        var provIndex = $(_config.provId).get(0).selectedIndex,   // 獲取省份的索引index
            elemHtml = '',
            prov,
            citys,
            provOpt;
        
        provOpt = $($(_config.provId + ' option')[0]).attr("value");
        var opthtml = '<option value="-1" data-name="請選擇" selected>請選擇</option>';

        // 如果省有請選擇的話 那麼相應的省要減一
        if(provOpt == -1) {
            provIndex--;
        }
        $(_config.cityId).empty();
        $(_config.areaId).empty();
        /*
         * 如果選擇的是 第一項 "請選擇" 的話 那麼省市區的value都為-1
         * 並且預設選中市 區的第一項 請選擇option
         */
        if(provIndex < 0){
            $(_config.provId).attr("data-code",'-1');
            $(_config.cityId).attr("data-code",'-1');
            $(_config.areaId).attr("data-code",'-1');

            $(_config.cityId).html(opthtml);
            $(_config.areaId).html(opthtml);
            return;
        }
        prov = _config.data[provIndex];
        citys = prov[2];
        elemHtml += '<option value="-1" data-name="請選擇">請選擇</option>';
        for(var m = 0; m < citys.length; m++) {
            var oneCity = citys[m];
            elemHtml += "<option value='"+oneCity[0]+"' data-name='"+oneCity[1]+"'>"+oneCity[1]+"</option>";
        }
        $(_config.cityId).html(elemHtml);

        if(_config.isSelect) {
            $($(_config.cityId + " option")[1]).attr("selected",'true');
            if(this.cityCode) {
                self._setSelectCode(_config.cityId,this.cityCode);
            }
        }
        self._selectChangeCode();

        _config.cityCallBack && $.isFunction(_config.cityCallBack) && _config.cityCallBack();
    },
    /*
     * 渲染市對應的區資料
     * @method _areaFunc {private}
     */
    _areaFunc: function(){
        var self = this,
            _config = self.config;

        var    provOpt = $($(_config.provId + ' option')[0]).attr("value"),
            cityOpt = $($(_config.cityId + ' option')[0]).attr("value");

        var provIndex = $(_config.provId).get(0).selectedIndex,
            cityIndex = $(_config.cityId).get(0).selectedIndex,
            elemHtml = "",
            prov,
            citys,
            areas,
            oneCity;
        var opthtml = '<option value="-1" data-name="請選擇" selected>請選擇</option>';
        
        /*
         * 如果省選擇了 "請選擇了" 那麼省和市自動切換到請選擇 那麼相應的索引index-1
         * 如果省沒有選擇 "請選擇",市選擇了 "請選擇" 那麼市的索引index - 1
         */
        if(provOpt == -1) {
            provIndex--;
            cityIndex--;

        }else if(provOpt != -1 && cityOpt == -1) {
            cityIndex--;
        }
        
        if(provIndex < 0 || cityIndex < 0){
            $(_config.cityId).attr("data-code",'-1');
            $(_config.areaId).attr("data-code",'-1');
            $(_config.areaId).html(opthtml);
            return;
        };
        prov = _config.data[provIndex];
        citys = prov[2];
        oneCity = citys[cityIndex];
        areas = oneCity[2];

        elemHtml += '<option value="-1" data-name="請選擇">請選擇</option>';
        if(areas != null) {
            for(var n = 0; n < areas.length; n++) {
                var oneArea = areas[n];
                elemHtml += "<option value='"+oneArea[0]+"' data-name='"+oneArea[1]+"'>"+oneArea[1]+"</option>";
            }
            
        }
        $(_config.areaId).html(elemHtml);
        
        if(_config.isSelect) {
            $($(_config.areaId + " option")[1]).attr("selected",'true');
            if(this.areaCode) {
                self._setSelectCode(_config.areaId,this.areaCode);
            }
        }
        self._selectChangeCode();

        _config.areaCallBack && $.isFunction(_config.areaCallBack) && _config.areaCallBack();
    },
     /*
     * 根據change事件來改變省市區select下拉框的data-code的值 
     * @method _changeSetCode private
     * @param selectId 省市區select dom節點
     */
    _changeSetCode: function(selectId){
        var self = this,
            _config = self.config;
        var idx = selectId.selectedIndex, //獲取選中的option的索引
            option,
            value,
            dataValue = $(_config.provId).val();
        var html = "<option data-name='請選擇' value='-1' selected>請選擇</option>",
            provOpt = $($(_config.provId + ' option')[0]).attr("value");

        if(idx > -1) {
            if(dataValue == -1) {
                if(provOpt != "-1") {
                    $(_config.provId).prepend(html);
                    $(_config.cityId).prepend(html);
                    $(_config.areaId).prepend(html);
                }
                $(_config.provId).attr("data-code",'');
                $(_config.cityId).attr("data-code",'');
                $(_config.areaId).attr("data-code",'');
            }else {
                option = selectId.options[idx];  //獲取選中的option元素
                value = $(option).val();
                $(selectId).attr("data-code",value);
            }
        }
    },
    _selectChangeCode: function(){
        var self = this,
            _config = self.config;

        // 省change事件時候 省select下拉框data-code也要變化
        var provId = document.getElementById(this.provid);
        self._changeSetCode(provId);

        // 市change事件時候 市select下拉框data-code也要變化
        var cityId = document.getElementById(this.cityid);
        self._changeSetCode(cityId);
        
        // 區change事件時候 市select下拉框data-code也要變化
        var areaId = document.getElementById(this.areaid);
        self._changeSetCode(areaId);
    },
     /*
     * 根據下拉框select屬性data-code值 來初始化省下拉框的值
     * @method _setSelectCode {private}
     * @param selectId 下拉框的Id
     */
    _setSelectCode: function(selectId,code){
        var self = this,
            _config = self.config;
            
        var optionElems = $(selectId + " option");
        
        $(optionElems).each(function(index,item){
            var curCode = $(item).val();
            if(curCode == code) {
                $(item).attr("selected",'true');
                $(selectId).attr("data-code",curCode);
                return;
            }
        });
    }
 };
View Code

JS省市區demo下載

 

         

相關文章