Reputation: 83
I have a Grid with two ScrollViewers, seperated by a GridSplitter. Both ScrollViewers have set a minimum size in the Grid's RowDefinitions. To set the GridSplitter programmatically, I have a binding to height of the bottom RowDefinition of the Grid.
Now, if I drag the GridSplitter up, first it hits the limit of the top viewer's minimum, but if I keep dragging up, the GridSplitter won't move, but WPF thinks that the size of the bottom scrollviewer DOES go up. All the way up to the point, where the bottom ScrollViewer is big enough to see all the content and remove the Scrollbar completely.
Here is the mainwindow xaml:
<Window x:Class="GridSplitTest.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:GridSplitTest"
mc:Ignorable="d"
Title="MainWindow" Height="500" Width="400">
<Grid Name="ParentGrid">
<Grid.Resources>
<local:RowHeightConverter x:Key="RowHeightConverter"/>
</Grid.Resources>
<Grid.RowDefinitions>
<RowDefinition MinHeight="200"/>
<RowDefinition Height="4"/>
<RowDefinition MinHeight="200" Height="{Binding BottomRowHeight,Mode=TwoWay,UpdateSourceTrigger=PropertyChanged, Converter={StaticResource RowHeightConverter}}"/>
</Grid.RowDefinitions>
<DockPanel Grid.Row="0">
<StackPanel DockPanel.Dock="Top" Orientation="Horizontal">
<TextBlock Text="{Binding BottomRowHeight, StringFormat='{}Bottom row height = {0}'}" Margin="10"/>
<TextBlock Tag="{Binding ElementName=ParentGrid, Path=ActualHeight}" Text="{Binding ElementName=ParentGrid, Path=ActualHeight, StringFormat='{}Grid height = {0}'}" Margin="10"/>
</StackPanel>
<ScrollViewer>
<ItemsControl ItemsSource="{Binding Texts}"/>
</ScrollViewer>
</DockPanel>
<GridSplitter Grid.Row="1" VerticalAlignment="Center" HorizontalAlignment="Stretch" Height="4" ShowsPreview="False" Background="DarkGray"/>
<ScrollViewer Grid.Row="2">
<ItemsControl ItemsSource="{Binding Texts}"/>
</ScrollViewer>
</Grid>
</Window>
The mainwindow.xaml.cs
using System.Collections.Generic;
using System.ComponentModel;
using System.Windows;
namespace GridSplitTest
{
public partial class MainWindow : Window, INotifyPropertyChanged
{
private List<string> _texts = new List<string>();
private double bottomRowHeight = 100;
public MainWindow()
{
InitializeComponent();
DataContext = this;
for (int i = 0; i < 100; i++)
{
_texts.Add(i.ToString());
}
}
public double BottomRowHeight
{
get => bottomRowHeight;
set
{
bottomRowHeight = value;
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(BottomRowHeight)));
}
}
public List<string> Texts => _texts;
public event PropertyChangedEventHandler PropertyChanged;
}
}
And finally, the converter:
using System;
using System.Diagnostics;
using System.Windows;
using System.Windows.Data;
namespace GridSplitTest
{
public class RowHeightConverter : IValueConverter
{
public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
{
return new GridLength((double)value);
}
public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
{
GridLength gridLength = (GridLength)value;
return gridLength.Value;
}
}
}
How can I avoid this behaviour? This is a small sample to demonstrate the problem. The actually project uses MVVM and a service to create the window. This makes it a problem to get to the Window class directly from the ViewModel
Upvotes: 0
Views: 31