I have the following XAML code:
<Grid Grid.Row="2" Name="grid_StatusBar">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="{Binding ElementName=wrapPanel, Path=ActualWidth}" />
<ColumnDefinition Width="30" />
</Grid.ColumnDefinitions>
<ProgressBar Grid.Column="0" HorizontalAlignment="Stretch" Margin="5,5,5,5" Name="progressBar1" VerticalAlignment="Stretch" />
<WrapPanel Grid.Column="1" Name="wrapPanel" HorizontalAlignment="Right">
<Label Content="1" Height="28" HorizontalAlignment="Right" Margin="0,0,0,0" Name="label_Dataset" VerticalAlignment="Stretch" Visibility="Collapsed" />
<Label Content="/20" Height="28" HorizontalAlignment="Right" Margin="0,0,0,0" Name="label_TotalDatasets" VerticalAlignment="Stretch" Visibility="Collapsed" />
<Label Content="ID:" Height="28" HorizontalAlignment="Right" Margin="0,0,0,0" Name="label_IDText" VerticalAlignment="Stretch" />
<Label Content="no id" Height="28" HorizontalAlignment="Right" Margin="0,0,0,0" Name="labelID" VerticalAlignment="Stretch" />
</WrapPanel>
<Button Grid.Column="2" Name="button_Help" Height="30" Width="30" Content="?" HorizontalAlignment="Right" VerticalAlignment="Stretch" Click="button_Help_Click" >
</Grid>
What i am trying to show the progressbar as wide as possible while changing the visibility of some of the labels and setting different texts (and therefore different lengths/widths.
I have then different functions:
- At program start the "no id" text of the
labelID
Label is replaced with an internal value. The width is updated: OK - With the code running I change the visibility of the first two labels, and the
ColumnDefinition.Width
is not updated and only the first two labels are shown (because there is not place enough for all the 4 of them to fit in the wrapPanel ActualWidth: ERROR! - If I change the
Visibility
property from the first two Labels fromCollapsed
toVisible
, from start the visibility of all the Labels areVisible
, and all the Labels are shown: OK - From the previous state I change visibility of the first two Labels to
Collapsed
, theColumnDefinition.Width
is updated and theProgressBar
is as wide as possible and all the text is shown: OK
Could anyone please help me? I do not understand why the width is not updated...
NOTE: The visibility is changed using two buttons in the window running the following code:
label_Dataset.Visibility = System.Windows.Visibility.Visible;
label_TotalDatasets.Visibility = System.Windows.Visibility.Visible;
EDIT: My target is to show the Visible Labels using the minimum space (in one line) in order to have the ProgressBar using the maximum width possible.
It is not possible to change the width of a parent element based on the width of a child. In your case, the column is the parent of the
WrapPanel
, so theActualWidth
of theWrapPanel
is not available until after the grid/column has already been sized.Even if you wrote code to try and circumvent this, you would still run into an issue, as the measure/layout sequence would become re-entrant. Whenever the size of the column changed, it would re-layout all the child controls, one of which is the
WrapPanel
. This would cause theActualWidth
of theWrapPanel
to be changed -- effectively causing an infinite loop. To prevent this stack overflow scenario, the framework immediately detects any re-entrancy in the layout/measure cycle and throws an exception.I'm not exactly sure what you are trying to achieve. Why do would you want the Labels in a
WrapPanel
? Surely you would always want the 4 labels to be on the same line, or at least on two lines.If this is the case, I would set the width of the second Column to "Auto" and put the labels in another container, i.e. one of the following:
If you want all the labels to wrap, as in a
WrapPanel
being forced to its minimum width, use:If you want all the labels to stay on the same line, use:
If you want two lines use: