一、目的

这篇文章主要是以如何实现联动下拉为核心,其要原理是利用两个下拉控件。默认两个下拉均为未选择状态,并且

父下拉中存在数据,子下来中没有数据。只有当用户选择某一个父下拉中的某条数据后,子下拉中才会显示所选父数据

的子数据。

注:使用的控件是基于telerik,如果你尚未安装请下载安装

二、实现

1.我们新建一个空的ASP.NET网站项目,并且在其中新建一个LinkageDropDown的Web页面,并添加一个App_

Code文件夹,在文件夹中新建一个名为DataModel的类文件。并且点击该文件,将生成操作改成编译,结果如图1.1。

图 1.1

2.在DataModel中创建模拟数据,代码如下

 public class DataModels
{
private DataTable table1 = new DataTable();
private DataTable table2 = new DataTable(); public DataModels()
{
table1.Columns.Add("id");
table1.Columns.Add("name"); table2.Columns.Add("id");
table2.Columns.Add("name");
table2.Columns.Add("bid"); AddData();
} protected void AddData()
{
DataRow dr = table1.NewRow();
dr["id"] = "";
dr["name"] = "大类一";
table1.Rows.Add(dr); dr = table1.NewRow();
dr["id"] = "";
dr["name"] = "大类二";
table1.Rows.Add(dr); dr = table1.NewRow();
dr["id"] = "";
dr["name"] = "大类三";
table1.Rows.Add(dr); dr = table1.NewRow();
dr["id"] = "";
dr["name"] = "大类四";
table1.Rows.Add(dr); dr = table1.NewRow();
dr["id"] = "";
dr["name"] = "大类五";
table1.Rows.Add(dr); dr = table1.NewRow();
dr["id"] = "";
dr["name"] = "大类六笑嘻嘻笑嘻嘻系";
table1.Rows.Add(dr); dr = table2.NewRow();
dr["id"] = "";
dr["name"] = "大类一的小类一";
dr["bid"] = "";
table2.Rows.Add(dr); dr = table2.NewRow();
dr["id"] = "";
dr["name"] = "大类一的小类二";
dr["bid"] = "";
table2.Rows.Add(dr); dr = table2.NewRow();
dr["id"] = "";
dr["name"] = "大类二的小类一";
dr["bid"] = "";
table2.Rows.Add(dr); dr = table2.NewRow();
dr["id"] = "";
dr["name"] = "大类二的小类二";
dr["bid"] = "";
table2.Rows.Add(dr); dr = table2.NewRow();
dr["id"] = "";
dr["name"] = "大类三的小类一";
dr["bid"] = "";
table2.Rows.Add(dr); dr = table2.NewRow();
dr["id"] = "";
dr["name"] = "大类三的小类二";
dr["bid"] = "";
table2.Rows.Add(dr); } public DataTable GetTable1()
{
return table1;
} public DataTable GetTable2()
{
return table2;
}

其中GetTable1返回大类的数据,GetTable2返回小类的数据。

3.在LinkageDropDown.aspx中拖放控件,最终代码如下:

     <form id="form1" runat="server">
<telerik:RadScriptManager ID="RadScriptManager1" runat="server"></telerik:RadScriptManager>
<telerik:RadAjaxManager ID="RadAjaxManager1" runat="server">
<AjaxSettings>
<telerik:AjaxSetting AjaxControlID="RadDropDownList1">
<UpdatedControls>
<telerik:AjaxUpdatedControl ControlID="RadDropDownList2" />
</UpdatedControls>
</telerik:AjaxSetting>
</AjaxSettings>
</telerik:RadAjaxManager>
<div style="width:100%;float:left;">
<div style="width: 150px; float: left; overflow: hidden;">
<telerik:RadDropDownList ValidationGroup="linkage" Width="150" AutoPostBack="true" DataTextField="name" DataValueField="id" ID="RadDropDownList1" runat="server" DefaultMessage="请选择大类" EnableAjaxSkinRendering="False" EnableViewState="False" OnSelectedIndexChanged="RadDropDownList1_SelectedIndexChanged" EnableEmbeddedBaseStylesheet="False" EnableEmbeddedScripts="False" EnableEmbeddedSkins="False" EnableTheming="False" Skin="MetroTouch"></telerik:RadDropDownList>
</div>
<div style="width: 150px; float: left; overflow: hidden; margin-left: 35px;">
<telerik:RadDropDownList ValidationGroup="linkage" Width="150" ID="RadDropDownList2" DataTextField="name" DataValueField="id" runat="server" DefaultMessage="请选择小类" EnableViewState="False" Skin="MetroTouch"></telerik:RadDropDownList>
</div>
</div>
<div>
<telerik:RadButton ID="RadButton1" ValidationGroup="linkage" CausesValidation="true" runat="server" Text="提交" Skin="MetroTouch" OnClick="RadButton1_Click"></telerik:RadButton>
</div>
</form>

其中需要重点说明的是父下拉控件的AutoPostBack必须手动设置为true,否则ajax下可能会无法触发后台事件。这里我们采用了

DefaultMessage属性用来这是没有选择时显示的信息,我相信很多人都会采用在DataTable插入一条数据,用来显示默认选择的状态,

或者把DataTable循环一遍,用创建子控件的方式一个一个添加进去。而这里我们没有这么做,而是直接将DataTable数据源绑定到控

件上去的。首先我们可以看到DataTextField属性以及DataValueField属性,分为表示将表中的哪一个字段的数据作为下拉显示的文本

以及作为选择后的值。

这里还有一点很重要,就是视图的大小,一个RadDropDownList控件默认情况下,会根据你需要显示的数据扩大ViewState。

这里我们仅仅只显示的几条,但是视图的却比原本增加了2行左右,是相当的庞大。所以这里我们干脆直接禁用了这两个下拉的视图

状态。可能你会想这样会造成什么后果,这里我们假设下你的做法,如果你只会在第一次才给下拉控件加载数据,并且在提交页面之

后不在加载数据给下拉控件,那么在不使用视图下你会看到当你点击提交之后,下拉中除了你所选的数据,其他的数据都不会存在了,

如果是聪明的人应该立即就能反应过来为什么我说视图的大小是根据你的数据大小,因为控件会把你的数据保存在视图中,当你点击

提交之后,控件会自动的从视图中读取你给这个控件加载的数据,重新加载。所以你就可以看到在你点击提交之后,触发后台的事件,

但是没有给这个控件绑定数据,然而在页面控件依然可以看到数据还是存在。我们禁用了视图是因为我们全过程采用的是ajax,所以

不会存在上述的问题,即我们可以禁用视图状态。

4.下面是后台代码

 public partial class LinkageDropdown : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
BindDropDown();
}
} protected void BindParentDropDown(DataTable data, String selid)
{
RadDropDownList1.DataSource = data;
RadDropDownList1.DataBind();
RadDropDownList1.SelectedValue = selid;
if ("".Equals(selid))
{
RadDropDownList1.SelectedIndex = -;
}
} protected void BindChildDropDown(DataTable data, String selid)
{
RadDropDownList2.DataSource = data;
RadDropDownList2.DataBind();
RadDropDownList2.SelectedValue = selid;
if ("".Equals(selid))
{
RadDropDownList2.SelectedIndex = -;
}
} protected void BindDropDown(string parvalue = "",string childvalue = "")
{
DataModels dm = new DataModels();
BindParentDropDown(dm.GetTable1(),parvalue);
if (String.IsNullOrEmpty(childvalue))
{
BindParentDropDown(dm.GetTable2(), childvalue);
}
} protected void RadDropDownList1_SelectedIndexChanged(object sender, Telerik.Web.UI.DropDownListEventArgs e)
{
DataModels dm = new DataModels();
var table = dm.GetTable2().AsEnumerable().Where(x => x["bid"].Equals(e.Value) ).Select(x => x);
if (table.Count() > )
{
BindChildDropDown(table.CopyToDataTable(),"");
}
} protected void RadButton1_Click(object sender, EventArgs e)
{
if (Page.IsValid)
{
Response.Write("the parent id is " + RadDropDownList1.SelectedValue + ",text is " + RadDropDownList1.SelectedText + "<br />");
Response.Write("the child id is " + RadDropDownList2.SelectedValue + ",text is " + RadDropDownList2.SelectedText + "<br />");
}
}
}

这里可以看到我的做法是只有第一次进到页面之后才会给控件加载数据,并且我仅仅只是加载了父下拉控件的数据,并没有加载子下拉控件的

数据,但是这里我却绑定了父控件的 SelectedIndexChanged 事件,同时这个事件的触发是采用ajax无刷新技术。其中可以看到这段代码:

var table = dm.GetTable2().AsEnumerable().Where(x => x["bid"].Equals(e.Value) ).Select(x => x);

这里我采用了lambda表示的方法,从子类表中查找那属于父类的子类数据,然后再通过CopyToDataTable转换成DataTable,这样才可以绑定

数据源。同时还要注意这里要判断存不存在数据,如果在不存在数据的情况下调用CopyToDataTable将会导致抛出异常。

然后我们看看两个下拉控件绑定数据源的地方:

         protected void BindParentDropDown(DataTable data, String selid)
{
RadDropDownList1.DataSource = data;
RadDropDownList1.DataBind();
RadDropDownList1.SelectedValue = selid;
if ("".Equals(selid))
{
RadDropDownList1.SelectedIndex = -;
}
}

重点是SelectedValue属性,因为在日常的开发中,我们有时需要在显示下拉的同时还要能够设置一个选项,但是我们只知道所选项的值,根本

无法判断所处的索引,所以这里我们就可以通过SelectedValue属性设置所选项的值,如果你设置的值不存在也不会导致异常。这里还要提及的一点

就是SelectedIndex,你可能会疑惑既然我们不知道索引为什么这里要赋为-1,其实这个主要是解决RadDropDownList控件中的一个Bug,当我们

选择一个大类,又选择了一个小类之后。我们改变所选大类,按道理小类应该是恢复未选择状态,但是我们实际发现子下拉控件会按照索引继续选择

新的小类中的数据,所以这里我们需要手动设置为-1,以恢复未选择状态。

5.最终效果图如下:

一进到页面:

选择一个大类:

选择一个小类:

改变大类:

点击提交:

你的联动够快够小吗——基于Telerik(ASP.NET平台)的更多相关文章

  1. 云计算:创业的好时机——上海够快网络科技有限公司总经理蒋烁淼专访(评价阿里云的OSS的4个优点)(够快科技正式宣布已成功挂牌新三板)

    云存储是云计算目前的热点之一,Dropbox.Box等产品的风靡,公司因此获得极高估值,都印证了这一点.但云存储对技术和资金要求都比较高,竞争也非常激烈,挑战巨大.国外云存储公司有亚马逊的云平台作为支 ...

  2. 够快网盘支持与iOS-ASIHTTPRequest框架学习

    够快网盘支持与iOS-ASIHTTPRequest框架学习 前段时间在公司的产品中支持了够快网盘,用于云盘存储. 在这个过程中,学习到了很多新的知识,也遇到了很多问题,在此记录一下. 首先就够快的AP ...

  3. 开源:矿Android新闻client,快、小、支持离线阅读、操作简单、内容丰富,形式多样展示、的信息量、全功能 等待(离开码邮箱)

    分享:矿Android新闻client.快.小.支持离线阅读.操作简单.内容丰富,形式多样展示.的信息量.全功能 等待(离开码邮箱) 历时30天我为了开发这个新闻clientAPP,下面简称觅闻 ht ...

  4. 小程序基于疼讯qcloud的nodejs开发服务器部署

        腾讯,疼讯,很疼. 请慎重看腾讯给出的文档,最好做一个笔记. 我只能说我能力有限,在腾讯云小程序的文档中跳了n天. 最后还是觉得记录下来,以防止我的cpu过载给烧了. 此文档是对<小程序 ...

  5. 微信小程序-基于canvas画画涂鸦

    代码地址如下:http://www.demodashi.com/demo/14461.html 一.前期准备工作 软件环境:微信开发者工具 官方下载地址:https://mp.weixin.qq.co ...

  6. 微信小程序基于swiper组件的tab切换

    代码地址如下:http://www.demodashi.com/demo/14010.html 一.前期准备工作 软件环境:微信开发者工具 官方下载地址:https://mp.weixin.qq.co ...

  7. 微信小程序基于scroll-view实现锚点定位

    代码地址如下:http://www.demodashi.com/demo/14009.html 一.前期准备工作 软件环境:微信开发者工具 官方下载地址:https://mp.weixin.qq.co ...

  8. 基于olami开放语义平台的微信小程序遥知之源码实现

    概述 实现一个智能生活信息查询的小秘书功能,支持查天气.新闻.日历.汇率.笑话.故事.百科.诗词.邮编.区号.菜谱.股票.节目预告,还支持闲聊.算24点.数学计算.单位换算.购物.搜索等功能. 使用方 ...

  9. 微信小程序-基于高德地图API实现天气组件(动态效果)

    微信小程序-基于高德地图API实现天气组件(动态效果) ​ 在社区翻腾了许久,没有找到合适的天气插件.迫不得已,只好借鉴互联网上的web项目,手动迁移到小程序中使用.现在分享到互联网社区中,帮助后续有 ...

随机推荐

  1. QuerySet创建新对象的方法和获取对象的方法

    新建一个对象的方法有以下几种: Person.objects.create(name=name,age=age) p = Person(name="WZ", age=23) p.s ...

  2. java 调用 r, Can't find dependent libraries

    rJava是一个R语言和Java语言的通信接口,通过底层JNI实现调用,允许在R中直接调用Java的对象和方法. 步骤: 1.本地系统: Win7 64bit 企业版, jdk1.8.0_45,R3. ...

  3. bootstrap分页插件--Bootstrap Paginator的使用&AJAX版备份(可单独使用)

    html部分: <ul class="pagination"></ul> <!--bootstrap3版本用ul包裹--> <div cl ...

  4. 8.11 CSS知识点4

    边框样式 1.边框宽度 border-width:medium | thin | thick | length border-top-width  设置上边框宽度 border-bottom-widt ...

  5. Delphi关于记录文件的操作

    http://www.cnblogs.com/railgunman/archive/2010/08/16/1801004.html Delphi关于记录文件的操作   本例子几个变量的说明TFileR ...

  6. LoadRunner ---检查点

    判断脚本是否执行成功是根据服务器返回的状态来确定的,如果服务器返回的HTTP状态为 200 OK ,那么VuGen 就认为脚本正确地运行了,并且是运行通过的.在绝大多数系统出错时会返回错误页面码? 不 ...

  7. 【BootStrap】 基础

    [BootStrap] 基础 一. 自适应(针对不同设备如手机平板笔电,使页面的宽度适应设备宽度) <meta name="viewport" content="w ...

  8. java1.7集合源码阅读:LinkedList

    先看看类定义: public class LinkedList<E> extends AbstractSequentialList<E> implements List< ...

  9. iOS button文字居中

    新建一个UIButton的category .h @interface UIButton (QXTitleInCenter) -(instancetype)init; @end .m @impleme ...

  10. java多线程详解(6)-线程间的通信wait及notify方法

    Java多线程间的通信 本文提纲 一. 线程的几种状态 二. 线程间的相互作用 三.实例代码分析 一. 线程的几种状态 线程有四种状态,任何一个线程肯定处于这四种状态中的一种:(1). 产生(New) ...