Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why does a WPF Popup close when its background area is clicked?

I have a WPF Popup control that contains some editing controls (list boxes, text boxes, check boxes) laid out with quite a bit of whitespace.

Popup.StaysOpen is set to False, which is required. If the user clicks elsewhere in the application, the editing operation should be considered aborted and the popup should close.

Unfortunately the popup also closes whenever the user clicks within the background region of the popup (the space between the edit controls).

I've tried setting the popup to be Focusable. I've also tried setting the popup's child (a Border) to be focusable. No luck on either front.

Furthermore, the mouse event seems to tunnel through the popup. Whatever element is underneath the popup when I click it becomes focused. This is despite both the Popup and the Border (into which I'm clicking) having both IsHitTestVisible and Focusable set to true.

like image 678
Drew Noakes Avatar asked Mar 06 '09 17:03

Drew Noakes


2 Answers

In the end, I found that the following worked. Given...

<Popup x:Name="_popup"
       StaysOpen="False"
       PopupAnimation="Slide"
       AllowsTransparency="True">

...I used this code in the constructor after calling InitializeComponent...

// Ensure that any mouse event that gets through to the
// popup is considered handled, otherwise the popup would close
_popup.MouseDown += (s, e) => e.Handled = true;
like image 196
Drew Noakes Avatar answered Nov 19 '22 01:11

Drew Noakes


It does seem odd that it would ignore Focusable on the Popup and Border. I was able to fix your problem by changing StaysOpen in a trigger when the mouse is over the Border:

<Grid xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
    <ToggleButton x:Name="btnPop" Content="Pop!" Width="100" Height="50"/>
    <Popup Placement="Bottom" PlacementTarget="{Binding ElementName=btnPop}" IsOpen="{Binding IsChecked, ElementName=btnPop}">
        <Popup.Style>
            <Style TargetType="{x:Type Popup}">
                <Setter Property="StaysOpen" Value="False"/>
                <Style.Triggers>
                    <DataTrigger Binding="{Binding IsMouseOver, ElementName=brd}" Value="True">
                        <Setter Property="StaysOpen" Value="True"/>
                    </DataTrigger>
                </Style.Triggers>
            </Style>
        </Popup.Style>
        <Border x:Name="brd" Background="White" BorderThickness="1" BorderBrush="Black">
            <StackPanel>
                <TextBox Margin="10"/>
                <TextBlock Text="Some text is here." Margin="10"/>
                <TextBox Margin="10"/>
            </StackPanel>            
        </Border>
    </Popup>
</Grid>
like image 7
Robert Macnee Avatar answered Nov 18 '22 23:11

Robert Macnee