I am using SelectionChanged in ComboBox item, but when I select the same item again the SelectionChanged function does not fire and I need it to do so. How can I tell it to fire no mater witch selection I do.
private void ComboBox_SelectionChanged4(object sender, SelectionChangedEventArgs e)
{
//do some stuff
}
XAML:
<ComboBox Height="30" Name="Combo4" Style="{StaticResource CategoryComboBox}" SelectionChanged="ComboBox_SelectionChanged4" Grid.ColumnSpan="2" Grid.Column="0">
<ComboBoxItem Content="ComboBox Item 1 (Example)" />
<ComboBoxItem Content="ComboBox Item 2 (Example)" />
<ComboBoxItem Content="ComboBox Item 3 (Example)" />
<ComboBoxItem Content="ComboBox Item 4 (Example)" />
</ComboBox>
Adding items:
for (int i = 0; i < Pr4.Count(); i++)
{
ComboBoxItem item = new ComboBoxItem();
item.Content = Pr4[i];
Combo4.Items.Add(item);
}
I used DropDownClosed, thank to - Clemens
I had the same question and I finally found the answer:
You need to handle BOTH the SelectionChanged event and the DropDownClosed like this:
In XAML:
<ComboBox Name="cmbSelect" SelectionChanged="ComboBox_SelectionChanged" DropDownClosed="ComboBox_DropDownClosed">
<ComboBoxItem>1</ComboBoxItem>
<ComboBoxItem>2</ComboBoxItem>
<ComboBoxItem>3</ComboBoxItem>
</ComboBox>
In C#:
private bool handle = true;
private void ComboBox_DropDownClosed(object sender, EventArgs e) {
if(handle)Handle();
handle = true;
}
private void ComboBox_SelectionChanged(object sender, SelectionChangedEventArgs e) {
ComboBox cmb = sender as ComboBox;
handle = !cmb.IsDropDownOpen;
Handle();
}
private void Handle() {
switch (cmbSelect.SelectedItem.ToString().Split(new string[] { ": " }, StringSplitOptions.None).Last())
{
case "1":
//Handle for the first combobox
break;
case "2":
//Handle for the second combobox
break;
case "3":
//Handle for the third combobox
break;
}
}
Behavior which uses DropDownOpen and DropDwonClose
public class InvokeIfSameElementSelectedBehavior : Behavior<ComboBox>
{
#region public ICommand Command
private static readonly PropertyMetadata CommandMetaData = new PropertyMetadata(default(ICommand));
public static readonly DependencyProperty CommandProperty = DependencyProperty.Register("Command",
typeof(ICommand), typeof(InvokeIfSameElementSelectedBehavior), CommandMetaData);
public ICommand Command
{
get { return (ICommand)GetValue(CommandProperty); }
set { SetValue(CommandProperty, value); }
}
#endregion //public ICommand Command
private bool _skipSelectionChanged;
private bool _popupMouseClicked;
private Popup _popup;
private object _previousValue;
protected override void OnAttached()
{
base.OnAttached();
if(AssociatedObject.IsLoaded)
AttachAllEvents();
else
AssociatedObject.Loaded += AssociatedObjectOnLoaded;
}
private void AssociatedObjectOnLoaded(object sender, RoutedEventArgs routedEventArgs)
{
AssociatedObject.Loaded -= AssociatedObjectOnLoaded;
AttachAllEvents();
}
protected override void OnDetaching()
{
base.OnDetaching();
AssociatedObject.SelectionChanged -= AssociatedObjectOnSelectionChanged;
AssociatedObject.DropDownOpened -= AssociatedObjectOnDropDownOpened;
AssociatedObject.DropDownClosed -= AssociatedObjectOnDropDownClosed;
if(_popup != null)
_popup.PreviewMouseLeftButtonDown -= PopupOnPreviewMouseLeftButtonDown;
}
private void AttachAllEvents()
{
AssociatedObject.SelectionChanged += AssociatedObjectOnSelectionChanged;
AssociatedObject.DropDownOpened += AssociatedObjectOnDropDownOpened;
AssociatedObject.DropDownClosed += AssociatedObjectOnDropDownClosed;
AssociatedObject.ApplyTemplate();
_popup = (Popup)AssociatedObject.Template.FindName("PART_Popup", AssociatedObject);
if(_popup != null)
_popup.PreviewMouseLeftButtonDown += PopupOnPreviewMouseLeftButtonDown;
}
private void AssociatedObjectOnDropDownOpened(object sender, EventArgs e)
{
_popupMouseClicked = false;
_previousValue = AssociatedObject.SelectedItem;
}
private void AssociatedObjectOnDropDownClosed(object sender, EventArgs e)
{
try
{
if (_popupMouseClicked && Equals(AssociatedObject.SelectedItem, _previousValue)) //SelectionChanged handles it if value are not the same
InvokeChangeCommand(AssociatedObject.SelectedItem);
}
finally
{
_popupMouseClicked = false;
}
}
private void PopupOnPreviewMouseLeftButtonDown(object sender, MouseButtonEventArgs e)
{
//ignore clicks on the scrollbars
if(e.Source is ScrollViewer)
return;
_popupMouseClicked = true;
}
private void AssociatedObjectOnSelectionChanged(object sender, SelectionChangedEventArgs e)
{
if (_skipSelectionChanged)
return;
try
{
_skipSelectionChanged = true;
if (e.AddedItems.Count != 1)
return;
InvokeChangeCommand(e.AddedItems[0]);
}
finally
{
_skipSelectionChanged = false;
}
}
private void InvokeChangeCommand(object item)
{
if (Command == null)
return;
if (!Command.CanExecute(item))
return;
Command.Execute(item);
}
}
Sample:
<ComboBox>
<i:Interaction.Behaviors>
<behaviors:InvokeIfSameElementSelectedBehavior Command="{Binding SelectionChangedCommand}"/>
</i:Interaction.Behaviors>
</ComboBox>
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With