系统开发中,经常遇到级联Select的状况,而级联的Select Option数据一般记录于DB,如果每次都重新写一套级联Select,工作将是繁琐滴。。。

一般来说,写一套级联的Select的几个步骤:

  1. 从DB读取Select Option的级联数据
  2. 将数据封装成JSON或xml传到前台
  3. 在前台由JS动态组装/填充Select元素
  4. 用JS调整各个级联Select之间的交互,如父Select值发生改变,重新填充子Select的选项,并清空子Select的已选值

  而这次,想写一套可重用的代码,便于以后有需要的时候可方便的搬进以后的项目,本代码依赖于

  1. Gson 2.2.4
  2. Jquery 1.6.1

  

  Kick-off:

  首先,由于是Demo,我们不从DB查询数据,只是用Collection直接模拟数据,为了便于生成JSON,使用Gson转换,为了组装级联数据结构方便,使用Selector.java和SelectorOption.java作为存储的结构:

 import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map; import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse; import com.google.gson.Gson;
import com.google.gson.GsonBuilder; public class CascapeSelectorServlet extends HttpServlet {
private static final long serialVersionUID = 1L; public CascapeSelectorServlet() {
super();
} protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
this.doPost(request, response);
} protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { /* country */
Selector countrySelector = new Selector("country", null, getCountry()); /* province */
Selector provinceSelector = new Selector("province", null, new HashMap());
List<SelectorOption> provinceList = getProvince();
for (int i = 0; i < provinceList.size(); i++) {
provinceSelector.put(provinceList.get(i).getParent(), provinceList.get(i));
} /* city */
Selector citySelector = new Selector("city", null, new HashMap());
List<SelectorOption> cityList = getCity();
for (int i = 0; i < cityList.size(); i++) {
citySelector.put(cityList.get(i).getParent(), cityList.get(i));
} Map dataMap = new HashMap();
dataMap.put("country", countrySelector);
dataMap.put("province", provinceSelector);
dataMap.put("city", citySelector); /* Gson */
GsonBuilder gsonBuilder = new GsonBuilder();
gsonBuilder.setPrettyPrinting();
Gson gson = gsonBuilder.create(); /* To json */
String json = gson.toJson(dataMap); System.out.println("json -> " + json);
response.getWriter().write(json);
} /**
* Analog data
* @return
*/
private List<SelectorOption> getCountry() {
List countryList = new ArrayList();
countryList.add(new SelectorOption("cn", "China"));
countryList.add(new SelectorOption("uk", "United Kingdom"));
countryList.add(new SelectorOption("ca", "Canada"));
countryList.add(new SelectorOption("us", "United States")); return countryList;
} /**
* Analog data
* @return
*/
private List<SelectorOption> getProvince() {
List provinceList = new ArrayList();
provinceList.add(new SelectorOption("hb", "Heibei", "cn"));
provinceList.add(new SelectorOption("zj", "Zhejiang", "cn"));
provinceList.add(new SelectorOption("gd", "Guangdong", "cn"));
provinceList.add(new SelectorOption("gx", "Guangxi", "cn"));
provinceList.add(new SelectorOption("ca", "California", "us")); return provinceList;
} /**
* Analog data
* @return
*/
private List<SelectorOption> getCity() {
List cityList = new ArrayList();
cityList.add(new SelectorOption("gz", "Guangzhou", "gd"));
cityList.add(new SelectorOption("nn", "Nanning", "gx"));
cityList.add(new SelectorOption("fs", "Foshan", "gd"));
cityList.add(new SelectorOption("hz", "Huizhou", "gd"));
cityList.add(new SelectorOption("la", "Los Angeles", "ca")); return cityList;
} }

CascapeSelectorServlet.java

  SelectorOption.java用于装一个Select的Option数据:

 public class SelectorOption {

     private String value;
private String name;
private String parent; public String getValue() {
return value;
} public void setValue(String value) {
this.value = value;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} public String getParent() {
return parent;
} public void setParent(String parent) {
this.parent = parent;
} public SelectorOption(String value, String name) {
super();
this.value = value;
this.name = name;
} public SelectorOption(String value, String name, String parent) {
super();
this.value = value;
this.name = name;
this.parent = parent;
} }

SelectorOption.java

  Selector.java用于装一个Selecti的数据:

 import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map; public class Selector { private String name;
private String parent;
private Map dataMap; public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} public String getParent() {
return parent;
} public void setParent(String parent) {
this.parent = parent;
} public Map getDataMap() {
return dataMap;
} public void setDataMap(Map dataMap) {
this.dataMap = dataMap;
} public Selector(String name, String parent, List dataList) {
super();
this.name = name;
this.parent = parent;
this.dataMap = new HashMap();
this.dataMap.put("default", dataList);
} public Selector(String name, String parent, Map dataMap) {
super();
this.name = name;
this.parent = parent;
this.dataMap = dataMap;
} public void put(String key, Object object) { if (key == null || key.length() == 0) {
return;
} if (object == null) {
return;
} if (this.dataMap == null) {
this.dataMap = new HashMap();
} if (this.dataMap.containsKey(key) && this.dataMap.get(key) != null) {
List tempList = (List)this.dataMap.get(key);
tempList.add(object);
} if (!this.dataMap.containsKey(key)) {
List tempList = new ArrayList();
tempList.add(object); this.dataMap.put(key, tempList);
} } }

Selector.java

  cascsel.js则用于处理各个级联Select之间的交互:

 /**
* Register & initialize select
*/
function registerSelector(data, array, index) {
if (!array || array.length == 0) {
return;
} if (index < 0 || index >= array.length) {
return;
} if (!data[array[index]]) {
return;
} var $select = $("[name='" + array[index] + "']"); /* Initialize default select */
var dataList = data[array[index]]["dataMap"]["default"];
if (dataList && dataList.length > 0) {
$select.empty();
for (var i = 0; i < dataList.length; i++) {
$select.append("<option value='" + dataList[i]["value"] + "'>" + dataList[i]["name"] + "</option>")
}
} /* Register onchange event for select */
if ((index + 1) < array.length && data[array[index + 1]]) {
$select.bind("change", function(event) {
var value = $select.val();
var dataList = data[array[index + 1]]["dataMap"][value]; $nextSelect = $("[name='" + array[index + 1] + "']");
/* If the option of select changes, refactor the cascape select */
if (dataList && dataList.length > 0) {
$nextSelect.empty();
for (var i = 0; i < dataList.length; i++) {
$nextSelect.append("<option value='" + dataList[i]["value"] + "'>" + dataList[i]["name"] + "</option>")
}
} else {
$nextSelect.empty();
} /* Trigger */
$nextSelect.trigger("change");
}); $select.trigger("change");
} registerSelector(data, array, index + 1); }

cascsel.js

  cascsel.jsp为Demo的展示页面(调用cascsel.js):

 <%@ page language="java" contentType="text/html; charset=utf-8"
pageEncoding="utf-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<script type="text/javascript" src="js/jquery-1.6.1.js"></script>
<script type="text/javascript" src="js/cascsel.js"></script>
<script type="text/javascript">
$().ready(function() { querySelector(); }); /**
* Get select json by ajax
*/
function querySelector() {
$.ajax({
url : "CascapeSelectorServlet",
dataType : "json",
type : "post",
contentType : "application/x-www-form-urlencoded; charset=utf-8",
cache : false,
error : function(dty, errorType) {
alert(errorType);
},
success : function(data) {
registerSelector(data, ["country", "province", "city"], 0);
}
});
} </script> <title>Cascape Select</title>
</head>
<body> <select name="country" ></select>
<select name="province" ></select>
<select name="city" ></select> </body>
</html>

cascsel.jsp

Enjoy it!

HTML的级联Select的更多相关文章

  1. MVVM架构~knockoutjs系列之级联select

    返回目录 对于下拉列表框的绑定在之前的knockoutjs文章中已经介绍过,今天主要说一下级联的select,事实上,在knockoutjs里,是以数据绑定为中心的,而数据是以面向对象为前提的,而对于 ...

  2. JS写的多级联select,如何取值

    var $ = function (id) {    return "string" == typeof id ? document.getElementById(id) : id ...

  3. Jquery 实现select 3级级联查询

    实现级联效果的思路: 1. 页面加载时,先显示第一级select,第二.三级的select隐藏,根据第一级select值的改变,再显示第二级select,依次类推: 2.只从后台获取第一级select ...

  4. jQuery操作select控件取值和设值

    1.级联select的操作,后一个select的值随着前一个select选中值变化 $(".select_A").change(function(){ $(".selec ...

  5. 从省市区多重级联想到的,react和jquery的差别

    在我们的前端项目里经常会用到级联的select,比如省市区这样.通常这种级联大多是动态的.比如先加载了省,点击省加载市,点击市加载区.然后数据通常ajax返回.如果没有数据则说明到了叶子节点.   针 ...

  6. AlloyTouch之select选择插件

    原文地址:https://github.com/AlloyTeam/AlloyTouch/wiki/Simple-Select 写在前面 很多情况下,产品希望统一安卓和IOS select交互和样式. ...

  7. AlloyTouch之无限循环select插件

    写在前面 当滚动的内容很多,比如闹钟里设置秒,一共有60项.让使用者从59ms滚回01ms是一件很痛苦的事情,所以: 在列表项太多的情况下,我们希望能够有个无限循环的滚动.00ms和01ms是无缝链接 ...

  8. 关键字(8):数据库记录的增删查改insert,delete,select,update

    insert:一般只要参数个数和类型没问题,不会插入异常 INSERT INTO t_pos_dynamic_map(autoid, lt_termno, lt_merchno) VALUES(SEQ ...

  9. search cascade select & AntD

    search cascade select & AntD Antd https://ant.design/components/cascader-cn/#components-cascader ...

随机推荐

  1. CSS3去除手机浏览器button点击出现的高亮框

    在工作中常常遇到在手机浏览器中浏览网页时.点击页面中的button或者是具备点击事件的元素,就会出现一个默认的高亮框.影响总体的感官体验. 能够用一个简单的css3属性来解决:tap-highligh ...

  2. windows命令行设置IP与DNS

    用dos命令修改IP等本地连接属性 平时我们改IP通常都在是窗口界面本地连接直接修改, 那在命令行也可以设置IP地址?当然可以,这里要用到netsh命令 .点击“开始”->“运行”,输入“cmd ...

  3. Nginx随笔

    1.用于代理与反代理,处理大量请求的工具. 2.主要有三大模块:handle.upstream.过滤模块.handle用于在nginx内部接到请求并进行处理的状况:upstream用于需要nginx接 ...

  4. 〖Linux〗Ubuntu13.10,声音图标调节音量失效的解决办法

    升级Ubuntu13.10,发现声音图标不能调节音量[XUbuntu13.10发行日志]: 临时解决办法: gvim /usr/share/dbus-1/services/indicator-soun ...

  5. str.format格式化用法(通过{}来替代%)

    # -*- coding: utf-8 -*- #python 27 #xiaodeng #str.format格式化用法(通过{}来替代%) ''' >>> help(format ...

  6. 使用String 的 intern做锁提高并发能力

    一个场景: 某段代码只对同一个ip过来的请求同步处理: 比如ip为a的请求进入了同步代码块,那么后续的ip为a的请求则在代码块外边等着,这时来了一个ip为b的请求,那么这个请求也可以进去,也就是a的所 ...

  7. MySQL Desc指令相关

    MySQL Desc指令相关   2011-08-09 11:25:50|  分类: my基本命令 |举报 |字号 订阅 1.desc tablename; 例如 :mysql> desc jo ...

  8. 通俗的理解HTTPS以及SSL中的证书验证

    一.HTTPS的安全性体现在哪 HTTP(超文本传输协议,Hyper Text Transfer Protocol)是我们浏览网站信息传输最广泛的一种协议.HTTPS(Hyper Text Trans ...

  9. Android API之android.os.Parcelable

    android.os.Parcelable Interface for classes whose instances can be written to and restored from a Pa ...

  10. springmvc之url参数传递

    在学习 Spring Mvc 过程中,有必要来先了解几个关键参数:    @Controller: 在类上注解,则此类将编程一个控制器,在项目启动 Spring 将自动扫描此类,并进行对应URL路由映 ...