zoukankan      html  css  js  c++  java
  • 自己动手做一个支持动态绑定的多选CheckBoxList

            有一个项目需要用到checkboxlist的多选,本以为生成几个层然后点点鼠标就搞定的,结果发现麻烦一大堆,因为CheckBoxList不支持多选.
            当我们调用SelectedValue的时候,他默认只返回选中的第一项.然后网上看大多数做法都是在页面内对items遍历然后找被selected的项,但我比较懒,比较喜欢绑定,FormView里面的绑定不用写一堆代码实在是说不过去的.
            于是,对CheckBoxList做个扩展看起来是个不错的方法.
            摆在我面前的有两条路,第一,重新SelectedValue使他支持多个项目,第二,弄一个新的SelectedValues属性.由于有SelectedIndex这种属性,似乎没法让他返回一个数组而不是数,而且我也不想看CheckBoxList都是如何调用这2个属性的,当然还有SelectedItem,所以我选择了后者.
            本着够用就OK的原则,添加了一个属性,SelectedValues,最初的实现方式如下.

    public string SelectedValues
            
    {
                
    get
                
    {
                    StringBuilder sb 
    = new StringBuilder();
                    
    foreach (ListItem li in this.Items)
                    
    {
                        
    if (li.Selected)
                        
    {
                            sb.Append(li.Value);
                            sb.Append(
    ",");
                        }

                    }

                    
    return sb.ToString();
                }

                
    set
                
    {
                    
    string[] values = value.Split(new char[]{','},StringSplitOptions.RemoveEmptyEntries);
                    
                    
    this.ClearSelection();
                    
                    
    foreach (string val in values)
                    
    {
                        ListItem li 
    = this.Items.FindByValue(val);
                        
    if (li != null)
                            li.Selected 
    = true;
                    }

                }

                
            }

    然后拖控件,放到FormView里面,弄好DataBinding跟数据源,更新,提交,看看数据库,Roles字段里面出来个"Administrators,"(顺便说一下,这个是用做自定义的一个权限管理的),恩,回去看的时候却发现CheckBoxList还是空的,我晕,Set出问题了.
    调试的时候发现value是有的,但是Items.Count==0,突然意识到现在还没有绑定数据....
    没办法,看看SelectedValue的实现方法吧..

    [Browsable(false), WebCategory("Behavior"), Bindable(true, BindingDirection.TwoWay), DefaultValue(""), DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), Themeable(false), WebSysDescription("ListControl_SelectedValue")]
    public virtual string SelectedValue
    {
        
    get
        
    {
            
    int selectedIndex = this.SelectedIndex;
            
    if (selectedIndex >= 0)
            
    {
                
    return this.Items[selectedIndex].Value;
            }

            
    return string.Empty;
        }

        
    set
        
    {
            
    if (this.Items.Count != 0)
            
    {
                
    if ((value == null|| (base.DesignMode && (value.Length == 0)))
                
    {
                    
    this.ClearSelection();
                    
    return;
                }

                ListItem item 
    = this.Items.FindByValue(value);
                
    if ((((this.Page != null&& this.Page.IsPostBack) && this._stateLoaded) && (item == null))
                
    {
                    
    throw new ArgumentOutOfRangeException("value", SR.GetString("ListControl_SelectionOutOfRange"new object[] this.ID, "SelectedValue" }));
                }

                
    if (item != null)
                
    {
                    
    this.ClearSelection();
                    item.Selected 
    = true;
                }

            }

            
    this.cachedSelectedValue = value;
        }

    }

     

    cachedSelectedValue,很明显了....他存了一下,肯定DataBound后调用.
    于是修改代码,下面贴出完整版:)

    using System;
    using System.Data;
    using System.Configuration;
    using System.Web;
    using System.Web.Security;
    using System.Web.UI;
    using System.Web.UI.HtmlControls;
    using System.Web.UI.WebControls;
    using System.Web.UI.WebControls.WebParts;
    using System.ComponentModel;
    using System.Text;
    [assembly: TagPrefix(
    "KingCMS.Web.UI""KingCMS")]
    namespace KingCMS.Web.UI
    {
        [ToolboxData(
    "<{0}:LoningCheckBoxList runat=server></{0}:LoningCheckBoxList>")]
        
    public class LoningCheckBoxList:CheckBoxList
        
    {
            [Category(
    "扩展")]
            
    private string selectedValues;
            
    public string SelectedValues
            
    {
                
    get
                
    {
                    StringBuilder sb 
    = new StringBuilder();
                    
    foreach (ListItem li in this.Items)
                    
    {
                        
    if (li.Selected)
                        
    {
                            sb.Append(li.Value);
                            sb.Append(
    ",");
                        }

                    }

                    
    return sb.ToString();
                }

                
    set
                
    {
                    
    string[] values = value.Split(new char[]{','},StringSplitOptions.RemoveEmptyEntries);
                    selectedValues 
    = value;
                    
    this.ClearSelection();
                    
                    
    foreach (string val in values)
                    
    {
                        ListItem li 
    = this.Items.FindByValue(val);
                        
    if (li != null)
                            li.Selected 
    = true;
                    }

                }

                
            }

            
    protected override void OnDataBound(EventArgs e)
            
    {
                
    base.OnDataBound(e);
                
    if (selectedValues != null)
                
    {
                    
    this.ClearSelection();
                    
    string[] values = selectedValues.Split(new char[] ',' }, StringSplitOptions.RemoveEmptyEntries);
                    
    foreach (string val in values)
                    
    {
                        ListItem li 
    = this.Items.FindByValue(val);
                        
    if (li != null)
                            li.Selected 
    = true;
                    }

                }

                
            }


        }

    }

    代码还有很多地方需要改进,比如每次都来个StringBuider,没有缓存等等...不过由于在后台了,所以我认为无所谓的,实现功能好了,如果您有好的改进,拿出来一起分享了:)

  • 相关阅读:
    bs4--基本使用
    UnicodeDecodeError: 'gbk' codec can't decode byte 0xae in position 167: illegal multibyte sequence
    linux系统安全审计简单设置
    系统安全设置部分项
    启用系统登录失败处理功能
    系统口令复杂度设置
    正则表达式
    python中的内置函数(bytearray)
    python中的内置函数(2)
    python中的内置函数(一)
  • 原文地址:https://www.cnblogs.com/loning/p/1132614.html
Copyright © 2011-2022 走看看