是否可以在设计器生成的代码中设置自定义组件/控件的自定义属性的序列化顺序?

时间:2015-05-21 03:38:04

标签: c# visual-studio code-generation windows-forms-designer

我正在开发一些带有自定义属性的自定义(继承)控件,我在适当的属性修饰后添加了设计时支持。

一切正常但我的问题是使用控件的* .Designer.cs文件中的自动生成的代码具有特定的顺序,它设置各种属性(基本属性和新属性)。这个顺序看起来像字母w.r.t.财产名称。

因此自动生成的代码如下所示:

// 
// myTabPage1
// 
this.myTabPage1.Identifier = "ID";
this.myTabPage1.Name = "myTabPage1";
this.myTabPage1.Size = new System.Drawing.Size(294, 272);
this.myTabPage1.Text = "TTT";

我希望它看起来像这样:

// 
// myTabPage1
// 
this.myTabPage1.Name = "myTabPage1";
this.myTabPage1.Size = new System.Drawing.Size(294, 272);
this.myTabPage1.Text = "TTT";
this.myTabPage1.Identifier = "ID";

我需要这样做的原因是因为设置Identifier属性会影响Text,然后会将其恢复为设计时值,从而取消设置Identifier的效果。

当然有简单的解决方法(最简单的解决方法是不设置Text属性,但是如果这不是设计时的“担心”,那将是很好的,因为这个设计有广泛的用途许多继承的控件类型及其实例中的模式。

设置Text以识别表单设计器上的控件(Identifier在设计时对Text没有影响)也很有帮助。

1 个答案:

答案 0 :(得分:2)

不,您不能影响序列化顺序。这是一般解决方案的常见问题,实现ISupportInitialize interface。您的BeginInit()方法在设计器开始分配属性之前调用,您通常会设置一个 bool 变量,以确保属性设置器没有意外的副作用。完成后调用EndInit()方法,并且所有属性都有一个值,您可以将变量设置回 false 并执行您需要做的任何事情来使用这些值。

您的问题对于控制问题并不具体,但可能的实现可能如下所示:

public partial class CustomControl : UserControl, ISupportInitialize {
    public CustomControl() {
        InitializeComponent();
    }
    private bool initializing;
    private string id = "";

    public string ID {
        get { return id; }
        set { id = value;
              if (!initializing) label1.Text = value;
        }
    }
    [Browsable(true), EditorBrowsable(EditorBrowsableState.Always)]
    [DesignerSerializationVisibility(DesignerSerializationVisibility.Visible)]
    public override string Text {
        get { return base.Text; }
        set {
            base.Text = value;
            if (!initializing && !this.DesignMode) label1.Text = value;
        }
    }

    public void BeginInit() {
        initializing = true;
    }

    public void EndInit() {
        initializing = false;
        label1.Text = ID;
    }
}

另请注意此代码中的[DesignerSerializationVisibility]属性,当您使用Hidden时,该属性根本不会被序列化。这可能是解决问题的简单方法。