自定义属性

本文关键字:自定义属性 | 更新日期: 2023-09-27 18:26:07

我正在创建一些自定义控件,这些控件继承自具有以下属性的基本自定义控件:

    public Color BorderColor
    {
        get { return BorderColor; }
        set
        {
            if (!FollowsScheme)
                BorderColor = value;
        }
    }
    public Color[] FillColors
    {
        get { return FillColors; }
        set
        {
            if (!FollowsScheme)
                FillColors = value;
        }
    }
    public bool FollowsScheme { get; set; }

我正在尝试这样做,如果用户将FollowsScheme设置为false,只有这样他们才能编辑BorderColor和FillColors属性。如果FollowsScheme为true,则它们无法编辑这两个属性。在这段代码中,您可以看到我尝试做的和认为会起作用的事情,但当我构建解决方案并将控件添加到窗体时,Visual Studio崩溃了。我该怎么做?

让我更好地解释一下,如果FollowsScheme设置为true,在OnPaint方法上,代码将基于BorderColor和FillColors属性绘制控件,该属性基于一个静态类,该类填充了我设计的主题的颜色。如果FollowsScheme设置为false,则OnPaint方法将采用BorderColor和FillColors属性并计算新方案,并将这些颜色设置为列出的私有属性,然后这些颜色将用于绘制控件。

自定义属性

要明白,当您向窗体中添加控件时,Visual Studio将运行呈现该控件所需的代码,以便在设计器中显示该控件。

您的代码抛出一个StackOverflowException,随后导致Visual Studio崩溃。

引发此异常是因为您的属性setter是无限递归的。解决方案是引入一个backing字段来保存这样的值:

private Color borderColor;
public Color BorderColor
{
    get { return this.borderColor; }
    set
    {
        if (!FollowsScheme)
            this.borderColor = value;
    }
}

您正在属性设置器中设置属性

public Color BorderColor
{
    get { return BorderColor; }
    set
    {
        if (!FollowsScheme)
            BorderColor = value;   // BOOM!
    }
}

您需要为您的属性使用一个支持成员变量,通常如下所示:

private Color borderColor;
public Color BorderColor
{
    get { return borderColor; }
    set
    {
        if (!FollowsScheme)
            borderColor = value;
    }
}