Reputation: 4907
I have got the following XAML:
<StackPanel HorizontalAlignment="Center">
<Image Name="logo" Source="logo.png" Margin="0,0,0,50"/>
<ScrollViewer>
<Dashboard_Control:AlignableWrapPanel x:Name="wrapPanel"/>
</ScrollViewer>
<TextBlock FontWeight="Bold" HorizontalAlignment="Center" x:Name="txtBottomText"></TextBlock>
</StackPanel>
I would like that the wrapPanel
is scrollable only, so that the txtBottomText
control will always be at the bottom as you scroll, and the logo
image control will always be at the top - essentially only allowing the wrapPanel
to be scrollable.
I have tried adding a ScrollViewer as shown above, however it never shows. I even tried adding a property to always have the vertical scrollbar, however it appears without letting me scroll (the scrollbar is disabled).
I suspect that this is because my wrapPanel's content is dynamically generated at run-time like so:
wrapPanel.Children.Add(content);
Any ideas what I can do to fix this?
Upvotes: 1
Views: 74
Reputation: 421
If the Height of your WrapPanel exceeds the height of the control or window where you have put the controls, the Textblock below the Wrap Panel inside the Stack Panel is put after the Wrap panel and so it is below the scroll area. To be able to leave the Textblock always visible you have two means: 1) limit the height of your Wrap panel 2) Use a container like a Grid with 3 rows instead of the stack panel and put the Row Heights of the Grid respectively to Auto, *, Auto so that the image on top and the textblock on bottom use the space of their content and the Scroll panel uses all the space remaining
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="*"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<Image Grid.Row ="0" Source="myimage.jpg" />
<ScrollViewer Grid.Row="1">
<WrapPanel Height="1200" Width="600">
<TextBlock>Ciao sono io</TextBlock>
</WrapPanel>
</ScrollViewer>
<TextBox Grid.Row="2" TextWrapping="Wrap" HorizontalAlignment="Stretch" VerticalAlignment="Stretch" Text="IO c'ero" />
</Grid>
Upvotes: 1
Reputation: 791
You have to set a fixed heigh to your scrollviewer - if not, the scrollviewer takes as much space as he needs, in order to show the complete content of its children.
Solutions:
Upvotes: 0
Reputation: 4978
It's not because of your wrapPanel's content. but because you're using a StackPanel to contain everything.
StackPanels grow indefinitely in the direction determined by their Orientation
property. By default, that's vertically.
In your case, that makes the ScrollViewer "think" it has enough available space to stretch itself to accomodate its content, instead of activating the scroll bars. So it simply gets bigger as the WrapPanel inside gets bigger, pushing the TextBlock down.
To avoid this, you need to use a different Panel that is able to properly assign the available space to each control. Like a Grid.
<Grid HorizontalAlignment="Center">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<Image Name="logo" Source="logo.png" Margin="0,0,0,50"/>
<ScrollViewer Grid.Row="1">
<Dashboard_Control:AlignableWrapPanel x:Name="wrapPanel"/>
</ScrollViewer>
<TextBlock Grid.Row="2" FontWeight="Bold" HorizontalAlignment="Center" x:Name="txtBottomText"></TextBlock>
</Grid>
I usually say that StackPanels tend to be overused :P They're practical and easy to use, but they have a bunch of quirks and limitations that make them not suitable for many situations, like this one.
EDIT: Make sure, also, that the Grid is not contained inside another vertical StackPanel, a Grid row with Height set to Auto
, or something like that.
Upvotes: 1