Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Disable Right click and enable left click for contextmenu in WPF using MVVM

Code:

<Button Style="{StaticResource HPForegroundStyle}" IsTabStop="False"                 
        Command="{Binding ForegroundPhoneCommand}"  Click="Button_Click">
                    <Button.ContextMenu>                   
                        <ContextMenu ItemsSource="{Binding OptionsMenuItemList}"                            ItemContainerStyle="{StaticResource ContextMenuItemStyle}" 
                                     IsOpen="{Binding IsMenuOpen}"                                        
                                     PlacementTarget="{Binding RelativeSourc={RelativeSource AncestorType={x:Type Button}}}">
                        </ContextMenu>
                    </Button.ContextMenu>
    </Button>

i am using MVVM pattern. In ViewModel i have a property 'IsMenuOpen' which controls context menu open close .Problem is that i'm able to disable right click and not able to show context menu on left click.

like image 786
suman Avatar asked Oct 27 '10 05:10

suman


3 Answers

You can check also ContextMenuService.IsEnabled attached property on the parent control. It will block only right click and you will still be able to show the menu manually on left click, so based on previous example:

<Button x:Name="btn" Click="btn_Click" ContextMenuService.IsEnabled="false">
    <Button.ContextMenu>
        <ContextMenu x:Name="popup">
         ...
        </ContextMenu>
    </Button.ContextMenu>
</Button>

private void btn_Click(object sender, RoutedEventArgs e)
{
    popup.Visibility = Visibility.Visible;
    popup.IsOpen = true;
}
like image 136
severian Avatar answered Oct 31 '22 09:10

severian


This worked for me using XAML similar to the question.

private bool _isMenuOpen = false;
public bool IsMenuOpen 
{
    get { return _isMenuOpen; }
    set 
    {
        // Don't allow the UI (right-click) to set this property to true
        if (!value)
            _isMenuOpen = value;
    }
}

private void Button_Click(object sender, RoutedEventArgs e)
{
    Button btn = sender as Button;
    _isMenuOpen = true;
    btn.ContextMenu.IsOpen = true;
}
like image 42
Bryan Bassett Avatar answered Oct 31 '22 09:10

Bryan Bassett


A few things to keep track of:

  1. Ensure that the DataContext of the ContextMenu is valid.
  2. Make sure that IsOpen is a TwoWay binding.
  3. If you're going to attempt left click opening, remember that the PlacementTarget is not valid, so you'll have to set Button.ContextMenu.PlacementTarget = this, and then IsMenuOpen = true to have it show up.

My code snippet for reference:

<Style x:Key="SubjectButtonStyle" TargetType="{x:Type Button}" BasedOn="{StaticResource CommandButtonStyle}">
<Setter Property="Foreground" Value="Green" />
<Setter Property="ContextMenu">
    <Setter.Value>
        <ContextMenu DataContext="{Binding PlacementTarget.DataContext.Manager, RelativeSource={RelativeSource Self}}" 
                     ItemsSource="{Binding SubjectManager.ContextMenuItems}"
                     IsOpen="{Binding SubjectManager.ContextMenuIsOpen, Mode=TwoWay}">
            <ContextMenu.ItemContainerStyle>
                <Style TargetType="MenuItem">
                    <Setter Property="Command" Value="{Binding OnClick}" />
                </Style>
            </ContextMenu.ItemContainerStyle>
        </ContextMenu>
    </Setter.Value>
</Setter>
<Style.Triggers>
    <Trigger Property="IsMouseOver" Value="True">
        <Setter Property="Foreground" Value="DarkGreen" />
    </Trigger>
</Style.Triggers>
</Style>

And in the view model:

public void ShowContextMenu(SearchCondition searchCondition, Button button)
{
    button.ContextMenu.DataContext = this;
    SubjectManager.OpenContextMenu();
}
like image 2
Balki Avatar answered Oct 31 '22 09:10

Balki