控件TT继承自TextBox,TT中有个public属性MyPro,类型的MyStruct定义为
public struct MyStruct 
{
  public byte i;
  public byte j;  public MyStruct(byte a, byte b)
  {
    i = a;
    j = b;
  }
}
可是为什么控件的属性窗口中,属性MyPro是灰色的?不能像控件的Padding或Size属性那样展开一个属性菜单,然后设置里面的值?

解决方案 »

  1.   

    因为吧struct作为属性的时候,get返回的是属性的副本,所以设计器对值类型属性设置为只读,因为你实际修改了副本的字段并不能对控件本身那个属性有改变。
    你用类就可以了。
      

  2.   

    因为你这里只定义了访问属性,没定义设置属性:
    public byte i;
    public byte j;
    改为:private byte _i;
    Public byte i
    {
      get {return _i;}
      set { _i=value;}
    }
    private byte _j;
    Public byte j
    {
      get {return _j;}
      set { _j=value;}
    }
      

  3.   

    属性上加标签[Browsable(true), Category("XX"), Description("XX")] 如果想自动选择 试试 枚举 (没试过)
      

  4.   

    我想当然了。看这个文章介绍的吧。
    http://hi.baidu.com/wanhongnan/blog/item/e0d9863de9901603baa1670a.html/cmtid/122369cfd1137331f9dc6164
      

  5.   

    我觉得用类,然后把get set 都写出来,一起实现吧
      

  6.   

    得指定自定义的TypeConverter,我写了个例子[DefaultProperty("Text")]
        [ToolboxData("<{0}:HasCustomClassProperty runat=server></{0}:HasCustomClassProperty>")]
        public class HasCustomClassProperty : WebControl
        {
            [TypeConverter(typeof(MyStructConverter))]
            [Browsable(true)]
            public MyStruct MyPro
            {
                get { return ViewState["MyPro"] == null ? default(MyStruct) : (MyStruct) ViewState["MyPro"]; }
                set { ViewState["MyPro"] = value; }
            }                protected override void RenderContents(HtmlTextWriter output)
            {
                output.Write(String.Format("i:{0}",MyPro.i));
                output.Write(String.Format("j:{0}", MyPro.j));
            }
        }    public class MyStructConverter : TypeConverter
        {
            public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType)
            {
                if (sourceType == typeof(String))
                {
                    return true;
                }            return base.CanConvertFrom(context, sourceType);
            }        public override object ConvertFrom(ITypeDescriptorContext context, System.Globalization.CultureInfo culture, object value)
            {
                if (value is String)
                {
                    String[] values = value.ToString().Split(',');
                    MyStruct result = new MyStruct(Byte.Parse(values[0]), Byte.Parse(values[1]));
                    return result;
                }
                else
                {
                    return base.ConvertFrom(context, culture, value);
                }
            }        public override object ConvertTo(ITypeDescriptorContext context, System.Globalization.CultureInfo culture, object value, Type destinationType)
            {
                if (destinationType == typeof(String))
                {
                    MyStruct myStruct = (MyStruct) value;
                    return String.Format("{0},{1}", myStruct.i, myStruct.j);
                }
                else
                {
                    return base.ConvertTo(context, culture, value, destinationType);
                }
            }        public override bool CanConvertTo(ITypeDescriptorContext context, Type destinationType)
            {
                if (destinationType == typeof(String))
                {
                    return true;
                }
                else
                {
                    return base.CanConvertTo(context, destinationType);
                }
            }
        }    [Serializable]
        public struct MyStruct
        {
            public byte i;
            public byte j;        public MyStruct(byte a, byte b)
            {
                i = a;
                j = b;
            }
        }
      

  7.   

    如果想展开分别设置i和j呢?,继承下ExpandableObjectConverter,并公布出i和j[DefaultProperty("Text")]
        [ToolboxData("<{0}:HasCustomClassProperty runat=server></{0}:HasCustomClassProperty>")]
        public class HasCustomClassProperty : WebControl
        {
            [TypeConverter(typeof(MyStructConverter))]
            [Browsable(true)]
            public MyStruct MyPro
            {
                get { return ViewState["MyPro"] == null ? default(MyStruct) : (MyStruct) ViewState["MyPro"]; }
                set { ViewState["MyPro"] = value; }
            }                protected override void RenderContents(HtmlTextWriter output)
            {
                output.Write(String.Format("i:{0}",MyPro.I));
                output.Write(String.Format("j:{0}", MyPro.J));
            }
        }    public class MyStructConverter : ExpandableObjectConverter
        {
            public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType)
            {
                if (sourceType == typeof(String))
                {
                    return true;
                }            return base.CanConvertFrom(context, sourceType);
            }        public override object ConvertFrom(ITypeDescriptorContext context, System.Globalization.CultureInfo culture, object value)
            {
                if (value is String)
                {
                    String[] values = value.ToString().Split(',');
                    MyStruct result = new MyStruct(Byte.Parse(values[0]), Byte.Parse(values[1]));
                    return result;
                }
                else
                {
                    return base.ConvertFrom(context, culture, value);
                }
            }        public override object ConvertTo(ITypeDescriptorContext context, System.Globalization.CultureInfo culture, object value, Type destinationType)
            {
                if (destinationType == typeof(String))
                {
                    MyStruct myStruct = (MyStruct) value;
                    return String.Format("{0},{1}", myStruct.I, myStruct.J);
                }
                else
                {
                    return base.ConvertTo(context, culture, value, destinationType);
                }
            }        public override bool CanConvertTo(ITypeDescriptorContext context, Type destinationType)
            {
                if (destinationType == typeof(String))
                {
                    return true;
                }
                else
                {
                    return base.CanConvertTo(context, destinationType);
                }
            }
        }    [Serializable]
        public struct MyStruct
        {
            private byte i;
            private byte j;        public MyStruct(byte a, byte b)
            {
                i = a;
                j = b;
            }        public byte J
            {
                get { return j; }
                set { j = value; }
            }        public byte I
            {
                get { return i; }
                set { i = value; }
            }
        }
      

  8.   

    那如果你想控制它在“源”视图中的数据怎么办,也就是序列化的时候,可以通过PersistenceMode来设置,具体 的值楼主可以看下MSDN里的详细介绍[PersistenceMode(PersistenceMode.InnerDefaultProperty)]
    public MyStruct MyPro结果<MyPro I="1" J="2" />这样易读多了