wpf - ¿Cómo puedo hacer que ScrollViewer funcione dentro de un StackPanel?
xaml (6)
Así es como funciona:
<Window x:Class="TabControl.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:TabControl"
Title="MainWindow" Height="300"
DataContext="{Binding RelativeSource={RelativeSource Self}}"
>
<StackPanel>
<ScrollViewer Height="{Binding RelativeSource={RelativeSource Mode=FindAncestor,AncestorType={x:Type Border}},Path=ActualHeight}" >
<StackPanel >
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/> <TextBlock Text="This is a test"/>
</StackPanel>
</ScrollViewer>
</StackPanel>
Al vincular la altura del ScrollViewer a la altura interna de la ventana.
La lógica del redimensionamiento es que debemos dar a cualquier elemento la altura de corrección o diseñar la vista para usar la altura de renderizado.
Salida:
En el siguiente WPF XAML, el ScrollViewer no funciona (muestra una barra de desplazamiento, pero no puede desplazarse y los contenidos salen de la ventana hacia la parte inferior).
Puedo cambiar el StackPanel externo a una Grilla y funcionará.
Sin embargo, en mi aplicación desde la que reproduje el siguiente código, necesito tener un StackPanel externo. ¿Qué tengo que hacer con el StackPanel para hacer que el ScrollViewer muestre una barra de desplazamiento utilizable? por ejemplo VerticalAlignment = "Stretch" Height = "Auto" no funciona.
<StackPanel>
<ScrollViewer>
<StackPanel>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
<TextBlock Text="This is a test"/>
</StackPanel>
</ScrollViewer>
</StackPanel>
De hecho, la forma en que resolví ese dileman fue eliminar el panel de la pila exterior y, en su lugar, establecer el scrollviewer en la posición que quería dentro de la grilla principal.
<Grid Style="{StaticResource LayoutRootStyle}">
<Grid.RowDefinitions>
<RowDefinition Height="160"/>
<RowDefinition Height="*"/>
</Grid.RowDefinitions>
<!-- Vertical scrolling grid used in most view states -->
<ScrollViewer Grid.Row="1" HorizontalScrollBarVisibility="Auto">
<StackPanel Orientation="Horizontal">
<GridView>
...
</GridView>
</StackPanel>
</ScrollViewer>
Esto también me estaba molestando por un tiempo, el truco es poner tu stackpanel dentro de un scrollviewer.
Además, debe asegurarse de establecer la propiedad CanContentScroll del visor de desplazamiento en True, aquí hay un ejemplo:
<ScrollViewer Grid.Row="1" Margin="299,12,34,54" Name="ScrollViewer1" VerticalScrollBarVisibility="Auto" HorizontalScrollBarVisibility="Auto" Height="195" CanContentScroll="True">
<StackPanel Name="StackPanel1" OverridesDefaultStyle="False" Height="193" Width="376" VerticalAlignment="Top" HorizontalAlignment="Left"></StackPanel>
</ScrollViewer>
Mover Grid.Row = "1" de StackPanel a ScrollViewer lo resolvió completamente para mí.
Tenía una larga lista de unos 40 elementos para mostrar en un StackPanel, pero solo se mostraban los primeros 20.
<ScrollViewer Grid.Row="1" VerticalScrollBarVisibility="Auto">
<StackPanel x:Name="ContentPanel" Margin="12,0,12,0">
<TextBlock Text="{Binding Line1}" Margin="9,-7,0,0" Style="{StaticResource PhoneTextTitle1Style}"/>
<TextBlock Text="" Margin="10,-2,10,0" Style="{StaticResource PhoneTextNormalStyle}" />
...
</StackPanel>
</ScrollViewer>
No se puede sin fijar la altura del StackPanel
. Está diseñado para crecer indefinidamente en una dirección. Aconsejaría usar un Panel
diferente. ¿Por qué "necesitas" tener un StackPanel
externo?
Tenga en cuenta que a veces puede tener un StackPanel sin darse cuenta. En mi caso tenía este código
<ScrollViewer>
<ItemsControl ItemsSource="{Binding Pages}"/>
</ScrollViewer>
que funcionó bien Las "Páginas" a las que hacía referencia el enlace eran UserControls realmente diferentes y complejos, y yo quería tener solo barras de desplazamiento en algunos de ellos. Así que eliminé el scrollviewer:
<ItemsControl ItemsSource="{Binding Pages}"/>
Y luego puse el ScrollViewer como el elemento superior en los controles de usuario donde los quería. Sin embargo, esto no funcionó. El contenido fluyó de la página. Al principio no pensé que esta pregunta / respuesta podría ayudarme, pero me di cuenta de que el Panel de artículo predeterminado de un ItemsControl es el StackPanel. Así que resolví mi problema especificando un ItemsPanel que no era el StackPanel:
<ItemsControl ItemsSource="{Binding Pages}">
<ItemsControl.ItemsPanel>
<ItemsPanelTemplate>
<Grid/>
</ItemsPanelTemplate>
</ItemsControl.ItemsPanel>
</ItemsControl>