簡體   English   中英

如何在 Windows 窗體設計器中保存用戶控件的結構屬性?

[英]How to save a struct property of a user control in Windows Forms Designer?

我已經檢查了這個問題的答案: Modifying structure property in a PropertyGrid

還有來自 .net 的SizeConverter

但沒有幫助,我的財產仍然沒有保存。


我有一個結構體、一個用戶控件和一個自定義類型轉換器。

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();
    }
}

編譯后,我將控件拖到一個窗體中,然后我可以在屬性窗口中看到屬性Bar.Text ,我也可以編輯該值,它似乎被保存了。


但是InitializeComponent方法中沒有生成任何內容

什么也沒有產生

因此,如果我重新打開設計器,屬性窗口中的文本字段將變為空。

請注意該結構沒有自定義構造函數,所以我不能使用InstanceDescriptor

我錯過了任何重要的步驟嗎?

您在類型描述符中缺少一些方法覆蓋:

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;
    }
}

並將構造函數添加到結構中:

[TypeConverter(typeof(BarConverter))]
public struct Bar
{
    public Bar(string text)
    {
        Text = text;
    }
    public string Text { get; set; }
}

這就是Bar屬性序列化的方式:

// 
// userControl11
// 
this.userControl11.Bar = new SampleWinApp.Bar("Something");

bar 屬性將在屬性網格中顯示如下圖,具有可編輯的Text屬性:

在此處輸入圖片說明

您可能還想通過覆蓋結構的ToString()方法為結構提供更好的字符串表示,並通過覆蓋CanConvertFromConvertFromPointConverterSizeConverter一樣使屬性可從屬性網格中的字符串轉換。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM