Search code examples
wpfwindow-resizeexpandersizetocontent

How to automatically resize to content a Window with an Expander control?


I'm trying to figure out how to resize the Window of my application after an Expander control has been expanded or collapsed. It must grow or shrink. All the cases I've seen before on the StackOverflow suggest to set SizeToContent="WidthAndHeight". Is it a right workflow or should I change the size manually?

The application is consist of the MainWindow with an Expander-based user control in a StackPanel:

<Window x:Class="WpfAppBlend.MainWindow"                                 
        Title="MainWindow" Width="517" Height="298"
        SizeToContent="Manual" ResizeMode="NoResize"
        SizeChanged="Window_SizeChanged">    
    <StackPanel>
        <local:UCForm/>
    </StackPanel>
</Window>

This is my UserControl:

    <UserControl x:Class="WpfAppBlend.UCForm"
                 d:DesignWidth="500" d:DesignHeight="320" 
                 Width="500" Height="320">
        <Grid>
           <Expander ExpandDirection="Down" Header="Bookmarks"
                     Expanded="Expander_Expanded"
                     Collapsed="Expander_Collapsed">
                    <TextBlock>
                        Some text here...
                    </TextBlock>
            </Expander> 
        </Grid>
    </UserControl>

In my UserControl code-behind I have two empty event handlers:

public partial class UCForm : UserControl
{
    private void Expander_Expanded(object sender, RoutedEventArgs e){
        // How to get the instance of the Main Window here
        // to change it's Height?
    }    
    private void Expander_Collapsed(object sender, RoutedEventArgs e){
        // How to get the instance of the Main Window here
        // to change it's Height?    
    }
}

And my MainWindow class looks as follows:

public partial class MainWindow : Window
{
    public MainWindow(){
        InitializeComponent();
    }    
    private void Window_SizeChanged(object sender, SizeChangedEventArgs e){                        
    }
}

This is what I've got:

enter image description here

Setting SizeToContent="WidthAndHeight" doesn't work for me. Expander expands but window size doesn't change.

UPDATED: The problem is solved now. The issue was at fixed height. So if you want to make SizeToContent to do all dirty work, — you should NEVER NEVER NEVER specify the Height of your UserControl (only Width) in the case of ExpandDirection="Down". When you specify a fixed Height of the UserControl you must to handle the size change by yourself within an Expanded() and Collapsed() handlers of your UserControl class. My application layout is fine now:

enter image description here


Solution

  • You can indeed use the SizeToContent="WidthAndHeight" option so that the Window automatically resizes to fit exactly its content.

    However, to make it work properly, you need to remove the Width="500" Height="320" properties from your UCForm user control, as they give the control (and thus the window content) a fixed height. Your Window will then resize as the UserControl resizes.


    As a side note:

    private void Expander_Expanded(object sender, RoutedEventArgs e){
        // How to get the instance of the Main Window here
        // to change it's Height?
    }
    

    You almost NEVER want to get the instance of MainWindow and resize it from here. The key principle here is decoupling: make your UCForm re-usable by not forcing it to be used inside a MainWindow. What if one day you want to use your control somewhere else (another window, another app, or even outside WPF)?