自定义服务器端的RadioButton控件实现单选功能 (转自博客园Charles2008)
2008-12-10 23:22
489 查看
在项目中常常需要这样的功能:把RadioButton控件放到GridView(容器)控件中,设置GroupName为固定的一个值的时候实现单选功能,但是当最终生成HTML页面的时候,生成的Name会用 INamingContainer的规则自动生成不同的Name,就不能达到实现单选的效果。 (Name不唯一造成)
问题:如果在容器控件(如GridView)中的模板列中放入Asp:RadioButton控件的时候,实现对列表中的RadioButton的单选,应该怎么实现呢?
有人建议用客户端控件,可以很好的实现绑定,但是后台只能获取到选中项的值,但有时候需要获取未被选中的值,这样的话用客户端控件是不能达到需要的效果的。
那么用服务器端的控件该怎样实现radiobutton的单选呢?
在网上查找了相关的解决方案,找到两种解决方案,但都不是那么令人满意。
1.通过JavaScript脚本设置生成的不唯一Name的radiobutton实现单选的效果.
当然这种通过JavaScript能达到想要的效果,也能实现其功能,但是毕竟Javascript语言是不稳定的。(用户禁用Javascript后发送到服务器后可能会引起一些未知的问题)。
2.通过asp.net Ajax框架中的UpdatePanel,当用户点击服务器端的asp:radioButton后发送到服务器端,执行服务器端的代码,让其实现单选,这样虽然能够实现,但是这样增加了客户端和服务器端数据的传输量。这是不推荐使用的。
思考:其实用实现单选功能,只需要把radiobutton的Name属性设置成一样就可以(这才是关键),但是由于Asp.net机制,放到容器控件中的Template控件中后,生成后的RadioButton的Name就不是唯一的的(模板行ID+radiobutton的ID)(如:Repeater1_ctl02_CustomerRadio1,Repeater1_ctl03_CustomerRadio1)
根据上面的思路:自己做一个自定义控件,实现像asp:radioButton那样的功能,又能实现在容器中的Template中也能实现唯一的ID(设置相同的GroupName即可)。根据这个思路,终于实现了,下面是相关的代码实现:请参考
public class SingleCheckRadio : WebControl, IPostBackDataHandler
{
public string GroupName
{
get
{
return ViewState["GroupName"] == null ? this.UniqueID : ViewState["GroupName"].ToString();
}
set
{
ViewState["GroupName"] = value;
}
}
public string Text
{
get
{
return ViewState["_text"] == null ? "" : ViewState["_text"].ToString();
}
set
{
ViewState["_text"] = value;
}
}
[DefaultValue(false)]
public Boolean Checked
{
get
{
object obj2 = this.ViewState["_checked"];
return ((obj2 != null) && ((bool)obj2));
}
set
{
ViewState["_checked"] = value;
}
}
protected override void OnInit(EventArgs e)
{
Page.RegisterRequiresPostBack(this);
base.OnInit(e);
}
protected override void Render(HtmlTextWriter writer)
{
string output = string.Empty;
if (Checked)
{//如果为true就设置为选择,否则的话不选中。
output = "<input id=/"" + this.ClientID + "/" type=/"radio/" name=/""+GroupName+"/" checked=/"checked/" value=/"" + this.ClientID + "/" />";
}
else
{
output = "<input id=/"" + this.ClientID + "/" type=/"radio/" name=/""+GroupName+"/" value=/"" + this.ClientID + "/" />";
}
if (!string.IsNullOrEmpty(Text))//如果用户设置了Text属性就增加一个label标签(这里类似于asp:radioButton的Text属性的实现)
{
output += "<label for=/"" + this.ClientID + "/">" + Text + "</label>";
}
writer.Write(output);
}
protected virtual bool LoadPostData(string postDataKey, NameValueCollection postCollection)
{
bool flag = false;
string str = postCollection[GroupName];
bool flag2 = string.Equals(str, this.ClientID);//这里是关键,比较用户选择的那个radiobutton,如果为true的话就把该Check属性设置为true,否则为false.(后怎样把用户选择的值保存下来)
flag = flag2 != this.Checked;
this.Checked = flag2;//这
return flag;
}
IPostBackDataHandler 成员#region IPostBackDataHandler 成员
bool IPostBackDataHandler.LoadPostData(string postDataKey, NameValueCollection postCollection)
{
return LoadPostData(postDataKey, postCollection);
}
public void RaisePostDataChangedEvent()
{
return;
}
#endregion
}
这样编写的自定义RadioButton控件,放到容器控件的Template中,生成的RadioButton的Name就是唯一的,都是用户设置的GroupName的值。
下面是根据上面开发的自定义控件做的测试:aspx页面如下:
<asp:Repeater ID="Repeater1" runat="server">
<ItemTemplate>
<cc1:SingleCheckRadio ID="SingleCheckRadio" Text='<%#DataBinder.Eval(Container.DataItem,"Name") %>' GroupName="test" runat="server" />
</ItemTemplate>
</asp:Repeater>
下面是后台.cs代码,比较简单就不多说了。(绑定数据并获取选择项radiobutton的text属性。)
public class Person
{
public string Name { get; set; }
public int Age { get; set; }
}
public partial class _Default : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
List<Person> Persons = new List<Person>();
for (int i = 0; i < 10; i++)
{
Person p = new Person();
p.Name = "Charles" + i;
p.Age = 21 + i;
Persons.Add(p);
}
Repeater1.DataSource = Persons;
Repeater1.DataBind();
}
}
protected void Button1_Click(object sender, EventArgs e)
{
string str = String.Empty;
foreach (RepeaterItem item in Repeater1.Items)
{
CustomerRadioNamespace.SingleCheckRadio btn = item.FindControl("SingleCheckRadio") as CustomerRadioNamespace.SingleCheckRadio;
if (btn.Checked == true)
{
str = btn.Text;
}
}
Response.Write(str);
}最后我们来看看生成的HTML源代码:(可以看出生成出来的Name就是程序中设置的GroupName属性且是唯一的,这样就能实现单选功能了)
Code
<div>
<input id="Repeater1_ctl00_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl00_SingleCheckRadio" /><label for="Repeater1_ctl00_SingleCheckRadio">Charles0</label>
<input id="Repeater1_ctl01_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl01_SingleCheckRadio" /><label for="Repeater1_ctl01_SingleCheckRadio">Charles1</label>
<input id="Repeater1_ctl02_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl02_SingleCheckRadio" /><label for="Repeater1_ctl02_SingleCheckRadio">Charles2</label>
<input id="Repeater1_ctl03_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl03_SingleCheckRadio" /><label for="Repeater1_ctl03_SingleCheckRadio">Charles3</label>
<input id="Repeater1_ctl04_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl04_SingleCheckRadio" /><label for="Repeater1_ctl04_SingleCheckRadio">Charles4</label>
<input id="Repeater1_ctl05_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl05_SingleCheckRadio" /><label for="Repeater1_ctl05_SingleCheckRadio">Charles5</label>
<input id="Repeater1_ctl06_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl06_SingleCheckRadio" /><label for="Repeater1_ctl06_SingleCheckRadio">Charles6</label>
<input id="Repeater1_ctl07_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl07_SingleCheckRadio" /><label for="Repeater1_ctl07_SingleCheckRadio">Charles7</label>
<input id="Repeater1_ctl08_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl08_SingleCheckRadio" /><label for="Repeater1_ctl08_SingleCheckRadio">Charles8</label>
<input id="Repeater1_ctl09_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl09_SingleCheckRadio" /><label for="Repeater1_ctl09_SingleCheckRadio">Charles9</label>
</div>
这样上面提到的效果实现了。而且兼容该控件放到其他子控件,还是比较实用的。
注:另外还可以为该控件定义事件,通过用户选择触发相应的服务器事件。(上面的代码未提供)
最后希望各位朋友们多多提出宝贵的意见,非常感谢。
Charles Chen
Regards
MSN:Charles.C.Chen@newegg.net
问题:如果在容器控件(如GridView)中的模板列中放入Asp:RadioButton控件的时候,实现对列表中的RadioButton的单选,应该怎么实现呢?
有人建议用客户端控件,可以很好的实现绑定,但是后台只能获取到选中项的值,但有时候需要获取未被选中的值,这样的话用客户端控件是不能达到需要的效果的。
那么用服务器端的控件该怎样实现radiobutton的单选呢?
在网上查找了相关的解决方案,找到两种解决方案,但都不是那么令人满意。
1.通过JavaScript脚本设置生成的不唯一Name的radiobutton实现单选的效果.
当然这种通过JavaScript能达到想要的效果,也能实现其功能,但是毕竟Javascript语言是不稳定的。(用户禁用Javascript后发送到服务器后可能会引起一些未知的问题)。
2.通过asp.net Ajax框架中的UpdatePanel,当用户点击服务器端的asp:radioButton后发送到服务器端,执行服务器端的代码,让其实现单选,这样虽然能够实现,但是这样增加了客户端和服务器端数据的传输量。这是不推荐使用的。
思考:其实用实现单选功能,只需要把radiobutton的Name属性设置成一样就可以(这才是关键),但是由于Asp.net机制,放到容器控件中的Template控件中后,生成后的RadioButton的Name就不是唯一的的(模板行ID+radiobutton的ID)(如:Repeater1_ctl02_CustomerRadio1,Repeater1_ctl03_CustomerRadio1)
根据上面的思路:自己做一个自定义控件,实现像asp:radioButton那样的功能,又能实现在容器中的Template中也能实现唯一的ID(设置相同的GroupName即可)。根据这个思路,终于实现了,下面是相关的代码实现:请参考
public class SingleCheckRadio : WebControl, IPostBackDataHandler
{
public string GroupName
{
get
{
return ViewState["GroupName"] == null ? this.UniqueID : ViewState["GroupName"].ToString();
}
set
{
ViewState["GroupName"] = value;
}
}
public string Text
{
get
{
return ViewState["_text"] == null ? "" : ViewState["_text"].ToString();
}
set
{
ViewState["_text"] = value;
}
}
[DefaultValue(false)]
public Boolean Checked
{
get
{
object obj2 = this.ViewState["_checked"];
return ((obj2 != null) && ((bool)obj2));
}
set
{
ViewState["_checked"] = value;
}
}
protected override void OnInit(EventArgs e)
{
Page.RegisterRequiresPostBack(this);
base.OnInit(e);
}
protected override void Render(HtmlTextWriter writer)
{
string output = string.Empty;
if (Checked)
{//如果为true就设置为选择,否则的话不选中。
output = "<input id=/"" + this.ClientID + "/" type=/"radio/" name=/""+GroupName+"/" checked=/"checked/" value=/"" + this.ClientID + "/" />";
}
else
{
output = "<input id=/"" + this.ClientID + "/" type=/"radio/" name=/""+GroupName+"/" value=/"" + this.ClientID + "/" />";
}
if (!string.IsNullOrEmpty(Text))//如果用户设置了Text属性就增加一个label标签(这里类似于asp:radioButton的Text属性的实现)
{
output += "<label for=/"" + this.ClientID + "/">" + Text + "</label>";
}
writer.Write(output);
}
protected virtual bool LoadPostData(string postDataKey, NameValueCollection postCollection)
{
bool flag = false;
string str = postCollection[GroupName];
bool flag2 = string.Equals(str, this.ClientID);//这里是关键,比较用户选择的那个radiobutton,如果为true的话就把该Check属性设置为true,否则为false.(后怎样把用户选择的值保存下来)
flag = flag2 != this.Checked;
this.Checked = flag2;//这
return flag;
}
IPostBackDataHandler 成员#region IPostBackDataHandler 成员
bool IPostBackDataHandler.LoadPostData(string postDataKey, NameValueCollection postCollection)
{
return LoadPostData(postDataKey, postCollection);
}
public void RaisePostDataChangedEvent()
{
return;
}
#endregion
}
这样编写的自定义RadioButton控件,放到容器控件的Template中,生成的RadioButton的Name就是唯一的,都是用户设置的GroupName的值。
下面是根据上面开发的自定义控件做的测试:aspx页面如下:
<asp:Repeater ID="Repeater1" runat="server">
<ItemTemplate>
<cc1:SingleCheckRadio ID="SingleCheckRadio" Text='<%#DataBinder.Eval(Container.DataItem,"Name") %>' GroupName="test" runat="server" />
</ItemTemplate>
</asp:Repeater>
下面是后台.cs代码,比较简单就不多说了。(绑定数据并获取选择项radiobutton的text属性。)
public class Person
{
public string Name { get; set; }
public int Age { get; set; }
}
public partial class _Default : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
List<Person> Persons = new List<Person>();
for (int i = 0; i < 10; i++)
{
Person p = new Person();
p.Name = "Charles" + i;
p.Age = 21 + i;
Persons.Add(p);
}
Repeater1.DataSource = Persons;
Repeater1.DataBind();
}
}
protected void Button1_Click(object sender, EventArgs e)
{
string str = String.Empty;
foreach (RepeaterItem item in Repeater1.Items)
{
CustomerRadioNamespace.SingleCheckRadio btn = item.FindControl("SingleCheckRadio") as CustomerRadioNamespace.SingleCheckRadio;
if (btn.Checked == true)
{
str = btn.Text;
}
}
Response.Write(str);
}最后我们来看看生成的HTML源代码:(可以看出生成出来的Name就是程序中设置的GroupName属性且是唯一的,这样就能实现单选功能了)
Code
<div>
<input id="Repeater1_ctl00_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl00_SingleCheckRadio" /><label for="Repeater1_ctl00_SingleCheckRadio">Charles0</label>
<input id="Repeater1_ctl01_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl01_SingleCheckRadio" /><label for="Repeater1_ctl01_SingleCheckRadio">Charles1</label>
<input id="Repeater1_ctl02_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl02_SingleCheckRadio" /><label for="Repeater1_ctl02_SingleCheckRadio">Charles2</label>
<input id="Repeater1_ctl03_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl03_SingleCheckRadio" /><label for="Repeater1_ctl03_SingleCheckRadio">Charles3</label>
<input id="Repeater1_ctl04_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl04_SingleCheckRadio" /><label for="Repeater1_ctl04_SingleCheckRadio">Charles4</label>
<input id="Repeater1_ctl05_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl05_SingleCheckRadio" /><label for="Repeater1_ctl05_SingleCheckRadio">Charles5</label>
<input id="Repeater1_ctl06_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl06_SingleCheckRadio" /><label for="Repeater1_ctl06_SingleCheckRadio">Charles6</label>
<input id="Repeater1_ctl07_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl07_SingleCheckRadio" /><label for="Repeater1_ctl07_SingleCheckRadio">Charles7</label>
<input id="Repeater1_ctl08_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl08_SingleCheckRadio" /><label for="Repeater1_ctl08_SingleCheckRadio">Charles8</label>
<input id="Repeater1_ctl09_SingleCheckRadio" type="radio" name="test" value="Repeater1_ctl09_SingleCheckRadio" /><label for="Repeater1_ctl09_SingleCheckRadio">Charles9</label>
</div>
这样上面提到的效果实现了。而且兼容该控件放到其他子控件,还是比较实用的。
注:另外还可以为该控件定义事件,通过用户选择触发相应的服务器事件。(上面的代码未提供)
最后希望各位朋友们多多提出宝贵的意见,非常感谢。
Charles Chen
Regards
MSN:Charles.C.Chen@newegg.net
相关文章推荐
- Android ListView中点击单行实现RadioButton的单选功能,自定义Item布局文件
- 自定义.NET Calarder日历控件2(实现博客园日历)
- 在DataGrid或DataList等容器上面实现RadioButton的单选功能
- 用自定义上传控件实现上传功能
- ASP.NET中服务器控件Button调用javascript代码运用正则表达式验证TextBox中输入的是否为正整数或正小数,符合要求则继续运行服务器端代码功能的实现
- 在WEB自定义控件中实现自动回传功能
- asp.net中Repeater控件里Radiobutton如何实现单选
- 图形的绘制,如何使用自定义画笔(颜色,线宽,线形)。如何为程序中添加选项菜单和选项设置对话框,如何使用标准颜色对话框,如何使用字体对话框,在选项对话框中实现预览功能。实现选项对话框和窗口类中的数据交换。如何改变对话框和控件的背景色,如何改变控件的文本颜色,
- vue - 使用vue实现自定义多选与单选的答题功能
- RadioGroup+RadioButton嵌套其他布局实现多行单选布局、自定义RadioButton选中和非选中样式、文字颜色
- Android控件笔记——使用RadioGroup和RadioButton实现单选效果
- ListView,Expandable 自定义单选,多选功能实现及注意
- 自定义GrildView实现单选功能
- C# winform项目中ListView控件使用CheckBoxes属性实现单选功能
- RadioButton在数据列表中实现单选功能
- 可以实现复合控件单选的radioButton
- 自定义.NET Calarder日历控件(实现博客园日历)
- RadioButtton java代码实现左右带自定义的图片,并且控制字体与图片间距,同时控件长度对其功能。
- jquery自定义风格独特的下拉列表控件(可实现单选和多选)
- 在GridView中的每行加入RadioButton,实现单选一行的功能