为什么在这种情况下ActualWidth和ActualHeight 0.0?

我在Canvas里面有一个Grid像这样定义:

 <Canvas x:Name="outerCanvas"> <Grid Grid.Row="1" Name="cGrid" ShowGridLines="True" Width="{Binding Path=ActualWidth, RelativeSource={RelativeSource AncestorType={x:Type Canvas}}}" Height="{Binding Path=ActualHeight, RelativeSource={RelativeSource AncestorType={x:Type Canvas}}}"> <Grid.ColumnDefinitions> <ColumnDefinition /> <ColumnDefinition/> <ColumnDefinition/> </Grid.ColumnDefinitions> <Grid.RowDefinitions> <RowDefinition /> <RowDefinition /> </Grid.RowDefinitions> <Rectangle Name="rectangle1" Stroke="Black" Fill="AntiqueWhite" /> <Rectangle Grid.Row="0" Grid.Column="1" Grid.ColumnSpan="1" Grid.RowSpan="1" Name="rectangle2" Stroke="Black" Fill="AliceBlue" /> <Rectangle Grid.Row="0" Grid.Column="2" Grid.ColumnSpan="1" Grid.RowSpan="1" Name="rectangle3" Stroke="Black" Fill="Aqua" /> <Rectangle Grid.Row="1" Grid.Column="0" Grid.ColumnSpan="3" Grid.RowSpan="1" Name="rectangle4" Stroke="Black" Fill="DarkViolet" /> </Grid> </Canvas> 

我的问题是,在窗口构造函数, InitializeComponents()之后Grid.ColumnDefinitions[0].ActualWidth或“任何矩形”。 ActualWidth全部设置为0.0(高度相同)。 我不知道该怎么做才能获得这些信息。 任何帮助?

观察:

  1. 我不是definig外部canvas的宽度和高度,但如果我这样做,它不能解决我的问题。
  2. 在运行时,我可以看到这个Canvas/Grid占据了整个窗口空间,所以它里面的每个矩形都有ActualWidth s和ActualHeight s
  3. 网格的宽度/高度绑定到canvas,但我试图删除这个绑定,我的问题仍然存在

在控制被测量和排列之前, ActualHeightActualWidth不会被设置。 通常在InitializeComponent()中没有任何东西导致一个度量,所以当它返回时它们仍然是零。

您可以通过在窗口的InitializeComponent()返回后手动调用窗口的Measure()Arrange()方法来强制计算这些值。

如果您正在调整内容:

 window.Measure(new Size(double.PositiveInfinity, double.PositiveInfinity)); window.Arrange(new Rect(0, 0, window.DesiredWidth, window.DesiredHeight)); 

如果您使用明确的窗口大小:

 window.Measure(new Size(Width, Height)); window.Arrange(new Rect(0, 0, window.DesiredWidth, window.DesiredHeight)); 

雷是正确的(+1),这是由于测量和安排通过还没有执行的事实。 但是,不要强制另一个布局传递(昂贵的),您可以等待,直到您的控件加载之前访问ActualXxx属性:

 public MyWindow() { Loaded += delegate { // access ActualWidth and ActualHeight here }; } 

在我们的例子中,解决scheme很简单,正如大家所说的,在Loaded完成之后需要调用ActualWidth和ActualHeight,所以我们只是将代码包装在一个调度器中,并将优先级设置为Loaded,如下所示:

 Dispatcher.Invoke(new Action(() => { graphHeight = ActualHeight; graphWidth = ActualWidth; }), DispatcherPriority.Loaded); 

ActualWidthActualHeight只有在XAML加载完成后才可用,在加载之前如何才能find这些参数?

使用Loaded事件,并在里面findActualWidthActualHeight

 private void me_Loaded(object sender, RoutedEventArgs e) { // do your stuffs here. }