代码之家  ›  专栏  ›  技术社区  ›  Aardvark

WPF/Silverlight依赖属性的延迟“呈现”?

  •  2
  • Aardvark  · 技术社区  · 17 年前

    有没有办法知道第一次通过XAML绑定访问依赖项属性的时间,以便在需要时实际“呈现”该属性的值?

    我有一个对象(从控件派生的类),它有几个PointCollection依赖属性,这些属性可能包含100或1000个点。每个属性可能会对点进行不同的排列,以用于不同类型的形状(多段线、多边形等-比这更复杂,但您可以理解)。通过模板,不同的XAML对象使用TemplateBinding来访问这些属性。由于我的对象使用模板,我永远不知道我的对象可能使用什么XAML形状,所以我永远不知道它们可能绑定或不绑定到什么属性。我只想在实际需要时填写这些PointCollection。

    我需要一个WPF和Silverlight兼容的解决方案。

    我希望有一个解决方案能够避免我的对象的用户遇到任何额外的复杂性。


    使现代化

    我发现的一种方法是使用 Value Converters

    起初我有3个副道具。但是,我可以只拥有一个属性(通常的形状),并使用一个转换后的值将这些点转换为其他2个所需的形状。这样我只在控件中创建一组点。仅在使用时才会产生将点转换为次形状的费用。现在,我的主控件不需要预测数据需要如何查找抛出到该控件的每个可能模板-现在是模板设计器的问题。


    当然,INotifyPropertyChanged和regular属性是处理此问题的推荐方法。

    2 回复  |  直到 10 年前
        1
  •  3
  •   Martin Liversage    17 年前

    您不必使用依赖属性来启用数据绑定。但是,接下来您必须实现 INotifyPropertyChanged 如果源位置的更改应该传播到绑定的目标位置。“normal”.NET属性很容易延迟加载,可能是这样的:

    PointCollection points
    
    public PointCollection Points {
      get {
        return this.points ?? (this.points = CreatePoints());
      }
    }
    
    PointCollection CreatePoints() {
      // ...
    }
    

    我不知道你怎么适应 InotifyProperty已更改 但是,您的控件向系统的其他部分提供数据听起来有点奇怪。可能需要创建一个视图模型,其中包含可以让控件数据绑定到的数据。

        2
  •  0
  •   Anvaka    17 年前

    如果我把你的问题转述给

    当依赖项属性发生更改时,如何获得通知?

    如果我是正确的,那么您可以注册自己的属性更改回调。总是有人叫它。无论是谁导致了绑定、样式或触发器的更改。以下代码段摘自MSDN文章“ Dependency Property Callbacks and Validation ":

    public static readonly DependencyProperty CurrentReadingProperty = 
    
        DependencyProperty.Register(
            "CurrentReading",
            typeof(double),
            typeof(Gauge),
            new FrameworkPropertyMetadata(
                Double.NaN,
                FrameworkPropertyMetadataOptions.AffectsMeasure,
                new PropertyChangedCallback(OnCurrentReadingChanged),
                new CoerceValueCallback(CoerceCurrentReading)
            ),
            new ValidateValueCallback(IsValidReading)
        );
        public double CurrentReading
        {
          get { return (double)GetValue(CurrentReadingProperty); }
          set { SetValue(CurrentReadingProperty, value); }
        }
    

    这里的要点是oncurrentradingchanged()方法。希望这有帮助:)。