C# - .Net4.0,Visual Studio 2010
出于某些原因,我使用单独的类来存储我的一些自定义控件的属性(绘制网格的属性)。这导致了一些问题,因为我希望能够调用" Invalidate()"任何时候编辑这些值(通过属性窗口或在运行时),以自动重绘控件。我能想到的最好的解决方案是在我的" GridProperties"中实现INotifyPropertyChanged。 class,在相关的" set"中随时触发PropertyChanged事件。调用访问器,然后从我的控件类订阅PropertyChanged事件处理程序以调用" Redraw"方法(只调用Invalidate())。
到目前为止,这是我的代码的缩短版本。
class MyControl : Control
{
[Browsable(true)]
public GridProperties Grid { get; set; }
public MyControl()
{
Grid = new GridValues();
Grid.Columns = 4;
Grid.Rows = 4;
Grid.ShowGridLines = true;
Grid.PropertyChanged += Redraw;
}
private void Redraw (object sender, PropertyChangedEventArgs e)
{
Invalidate();
}
protected override void OnPaint(PaintEventArgs e)
{
base.OnPaint(e);
//draw gridlines
//draw columns/ rows
}
}
class GridProperties : INotifyPropertyChanged
{
private int columns;
private int rows;
private bool showGridLines;
public int Columns
{
get { return columns; }
set
{
if (columns != value)
{
columns = value;
NotifyPropertyChanged("Columns");
}
}
}
public int Rows...
//same kinda deal for rows & showGridLines
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged(string info)
{
if (PropertyChanged != null)
PropertyChanged(this, new PropertyChangedEventArgs(info));
}
}
我的期望:随着Grid.Columns / Grid.Rows / Grid.ShowGridLines值以任何方式更改(希望通过属性窗口),也可以随时调用Redraw。
会发生什么:Redraw永远不会被调用,除非我在MyControl中使用一个全新的方法做这样的事情:
Grid.PropertyChanged += Redraw;
Grid.ShowGridLines = false;
这在运行期间有效,但是这使得使用事件管理器失败了,因为我可以设置值,然后每次调用Invalidate,并且它对通过属性窗口所做的任何更改都没有帮助。
如果有人能让我了解我做错了什么,或者是否有更好的方式,我真的很感激。老实说,我甚至不确定是否订阅会员的活动经理是好的做法。
答案 0 :(得分:1)
感谢Gusman的解决方案。我没有从MyControl的构造函数中连接到PropertyChanged,而是从Grid的setter中连接到它,如下所示:
private GridProperties grid;
[Browsale(true)]
public GridProperties Grid
{
get
{
return grid;
}
set
{
if(grid! = null)
grid.PropertyChanged -= Redraw;
grid = value;
grid.PropertyChanged += Redraw;
}
}
我只能假设某些东西正在某处替换我的GridProperties对象。无论哪种方式,任何时候访问Grid的setter我只是取消挂钩/并重新挂钩PropertyChanged事件管理器,现在无论是通过代码还是从属性窗口更改Grid的值,屏幕都会更新。