Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/asp.net-core/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 更新子属性时更新依赖项属性_C#_Wpf_Wpf Controls - Fatal编程技术网

C# 更新子属性时更新依赖项属性

C# 更新子属性时更新依赖项属性,c#,wpf,wpf-controls,C#,Wpf,Wpf Controls,我有一个继承canvas的类,它具有以下依赖属性 public class StorageCanvas : Canvas { public readonly static DependencyProperty StorageProperty = DependencyProperty.Register( "Storage", typeof(Polygon), typeof(StorageCanvas)); public Polygon Storage { get { ret

我有一个继承canvas的类,它具有以下依赖属性

public class StorageCanvas : Canvas
{
 public readonly static DependencyProperty StorageProperty = DependencyProperty.Register(
  "Storage",
  typeof(Polygon),
  typeof(StorageCanvas));

 public Polygon Storage
 {
  get { return (Polygon) GetValue(StorageProperty); }
  set { SetValue(StorageProperty, value); }
 }
}

存储
多边形
已更改/更新时,我是否可以以某种方式使依赖项属性“更新”,而不是要求用新实例替换多边形?

使用“渲染元数据”选项注册依赖项属性


好的
多边形。点
是一个,因此您可以订阅它的
Changed
事件,然后按照@dowhilefor的建议调用
InvalidateVisual()

public class StorageCanvas : Canvas {
  public static readonly DependencyProperty StorageProperty = DependencyProperty.Register(
    "Storage",
    typeof(Polygon),
    typeof(StorageCanvas),
    new FrameworkPropertyMetadata(null, PropertyChangedCallback));

  public Polygon Storage {
    get {
      return (Polygon)GetValue(StorageProperty);
    }
    set {
      SetValue(StorageProperty, value);
    }
  }

  private static void PropertyChangedCallback(
    DependencyObject dependencyObject, DependencyPropertyChangedEventArgs args) {
    var currentStorageCanvas = dependencyObject as StorageCanvas;
    if (currentStorageCanvas == null)
      return;
    var oldPolygon = args.OldValue as Polygon;
    if (oldPolygon != null)
      oldPolygon.Points.Changed -= currentStorageCanvas.PointsOnChanged;
    var newPolygon = args.NewValue as Polygon;
    if (newPolygon == null)
      return;
    newPolygon.Points.Changed += currentStorageCanvas.PointsOnChanged;

    // Just adding the following to test if updates are fine.
    currentStorageCanvas.Children.Clear();
    currentStorageCanvas.Children.Add(newPolygon);
  }

  private void PointsOnChanged(object sender, EventArgs eventArgs) {
    InvalidateVisual();
  }
}
因此,现在如果
存储
中的任何
发生了更改,而没有实际重新创建整个对象,
InvalidateVisual()
将被触发


这个概念只是订阅
pointscolection
Changed
事件。根据您的需求和逻辑,您需要解决这样一个问题:是否为您做正确的事情。

您所说的更新是什么意思?重画?重新评估?重播?谁在更换存储。每次属性更改时盲目更新是不明智的。但您可以使用Invalidate方法(如InvalidateVisual)自己触发它。此外,您还可以将属性的元数据更改为自动。如果更改了,我将调用Invalidate函数,这对您的存储不起作用,因为它通过调用setter来工作。我认为,您可以使用dependency property
回调
验证
。有关详细信息,请参阅。@dowhilefor我想在多边形
点发生更改时在画布上重新绘制多边形。
InvalidateVisual()
是触发重新绘制的非常重的方法。如果控件的大小没有更改,请使用
AffectsRender
或在
OnRender()
期间将
DrawingGroup
添加到
DrawingContext
,然后随时可以
DrawingGroup.Open()
并更改视觉效果。