[英]How to save a struct property of a user control in Windows Forms Designer?
I've checked the answers of this question: Modifying structure property in a PropertyGrid我已经检查了这个问题的答案: Modifying structure property in a PropertyGrid
And also SizeConverter
from .net.还有来自 .net 的
SizeConverter
。
But not helpful, my property is still not saved.但没有帮助,我的财产仍然没有保存。
I have a struct, a user control, and a custom type converter.我有一个结构体、一个用户控件和一个自定义类型转换器。
public partial class UserControl1 : UserControl
{
public Bar bar { get; set; } = new Bar();
}
[TypeConverter(typeof(BarConverter))]
public struct Bar
{
public string Text { get; set; }
}
public class BarConverter : ExpandableObjectConverter
{
public override bool GetCreateInstanceSupported(ITypeDescriptorContext context)
{
return true;
}
public override object CreateInstance(ITypeDescriptorContext context, IDictionary propertyValues)
{
if (propertyValues != null && propertyValues.Contains("Text"))
return new Bar { Text = (string)propertyValues["Text"] };
return new Bar();
}
}
After compile, I drag the control in a form then I can see the property Bar.Text
showed in the properties window, I also can edit the value and it seems be saved.编译后,我将控件拖到一个窗体中,然后我可以在属性窗口中看到属性
Bar.Text
,我也可以编辑该值,它似乎被保存了。
But nothing is generated in the InitializeComponent
method但是
InitializeComponent
方法中没有生成任何内容
So if I reopen the designer, the Text field in the properties window become empty.因此,如果我重新打开设计器,属性窗口中的文本字段将变为空。
Please notice the struct hasn't a custom constructor, so I cannot use InstanceDescriptor
.请注意该结构没有自定义构造函数,所以我不能使用
InstanceDescriptor
。
Do I miss any important steps?我错过了任何重要的步骤吗?
You are missing a few method overrides in the type descriptor:您在类型描述符中缺少一些方法覆盖:
public class BarConverter : ExpandableObjectConverter
{
public override bool CanConvertTo(ITypeDescriptorContext context, Type destinationType)
{
if (destinationType == typeof(InstanceDescriptor))
return true;
return base.CanConvertTo(context, destinationType);
}
public override object ConvertTo(ITypeDescriptorContext context,
CultureInfo culture, object value, Type destinationType)
{
if (destinationType == typeof(InstanceDescriptor))
{
ConstructorInfo ci = typeof(Bar).GetConstructor(new Type[] { typeof(string) });
Bar t = (Bar)value;
return new InstanceDescriptor(ci, new object[] { t.Text });
}
return base.ConvertTo(context, culture, value, destinationType);
}
public override object CreateInstance(ITypeDescriptorContext context,
IDictionary propertyValues)
{
if (propertyValues == null)
throw new ArgumentNullException("propertyValues");
object text = propertyValues["Text"];
return new Bar((string)text);
}
public override bool GetCreateInstanceSupported(ITypeDescriptorContext context)
{
return true;
}
}
And add constructor to the struct:并将构造函数添加到结构中:
[TypeConverter(typeof(BarConverter))]
public struct Bar
{
public Bar(string text)
{
Text = text;
}
public string Text { get; set; }
}
And this is how the Bar
property serializes:这就是
Bar
属性序列化的方式:
//
// userControl11
//
this.userControl11.Bar = new SampleWinApp.Bar("Something");
And the bar property will be shown like following image in property grid, having Text
property editable: bar 属性将在属性网格中显示如下图,具有可编辑的
Text
属性:
You may also want to provide a better string representation for the struct by overriding its ToString()
method of the struct, and also make the property convertible from string in property grid, by overriding CanConvertFrom
and ConvertFrom
like PointConverter
or SizeConverter
.您可能还想通过覆盖结构的
ToString()
方法为结构提供更好的字符串表示,并通过覆盖CanConvertFrom
和ConvertFrom
像PointConverter
或SizeConverter
一样使属性可从属性网格中的字符串转换。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.