First off you have to retain the first part's height. If you auto size the Expander area you could end up just squashing the first control so you need to set the first row to Auto and/or a MinHeight
The expander rows you do want to use Auto height so that when collapsed it won't take up space for the others, but with two expanders the maximum heights are going to be dependent on the expanded state of the other. There are a lot simpler approaches for sizing one expander correctly.
Expanders are infinite height controls like the StackPanel, meaning they aren't bounded by the limits of their container. So this means if you have a large content and you don't set it's maximum height the first expander could blow the bottom expander off the screen.
The trick in this case is using a size bounded control as a placeholder to get the remaining size. There's actually a few situations that makes life a bit simpler...
Below is a sample you can play around with that should work for you:
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<TextBlock Text="Fixed Line"/>
<Rectangle x:Name="RectangleSizeHolder"
Grid.Row="1"
SizeChanged="RectangleSizeHolder_SizeChanged"/>
<Grid Grid.Row="1">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<Expander x:Name="FirstExpander"
Grid.Row="0"
Height="Auto"
MinHeight="30"
Header="First Header"
Expanded="ExpanderChanged"
Collapsed="ExpanderChanged">
<Expander.Content>
<ScrollViewer VerticalScrollBarVisibility="Auto">
<DockPanel Height="1000"
LastChildFill="False">
<TextBlock DockPanel.Dock="Top" Text="Top First"/>
<TextBlock DockPanel.Dock="Bottom" Text="Bottom First"/>
</DockPanel>
</ScrollViewer>
</Expander.Content>
</Expander>
<Expander x:Name="SecondExpander"
Grid.Row="1"
Height="Auto"
MinHeight="30"
Header="Second Header"
Expanded="ExpanderChanged"
Collapsed="ExpanderChanged">
<Expander.Content>
<ScrollViewer VerticalScrollBarVisibility="Auto">
<DockPanel Height="1000"
LastChildFill="False">
<TextBlock DockPanel.Dock="Top" Text="Top Second"/>
<TextBlock DockPanel.Dock="Bottom" Text="Bottom Second"/>
</DockPanel>
</ScrollViewer>
</Expander.Content>
</Expander>
</Grid>
With code behind:
private void ExpanderChanged(object sender, RoutedEventArgs e)
{
SetHeights();
}
private void RectangleSizeHolder_SizeChanged(object sender, SizeChangedEventArgs e)
{
SetHeights();
}
private void SetHeights()
{
FirstExpander.MaxHeight = !SecondExpander.IsExpanded ? RectangleSizeHolder.ActualHeight - SecondExpander.MinHeight :
RectangleSizeHolder.ActualHeight / 2;
SecondExpander.MaxHeight = !FirstExpander.IsExpanded ? RectangleSizeHolder.ActualHeight - FirstExpander.MinHeight :
RectangleSizeHolder.ActualHeight / 2;
}