1

I have some ComboBox controls, each with some values. Each selected value triggers one of my events. When item selected from ComboBoxA, my event is triggerd with the value of the selected item. When one of my combo boxes is just opened and closed, no value changed in it, the event is not triggerd (this is the default behaviour of a combobox). But this is not what i need.

What i did, is to create a behavior that will associate with the DropDownClosed event, but i don't know how to trigger the SelectionChanged event.

Edit:

This question can be generalized: How to 'manually' trigger an event of a UI control? or - Is there a way to invoke the methods assosiated with an event?

Edit 2:

I'll try to explain the problem more clearly. I have this code, which takes a list of items, and present them as categories (Radio button) and items under category (ComboBox inside RadioButton). When selecting an item - the selection changed event is triggerd. OK! when selecting another radio button - an event is triggered. OK!!

Special case that not work (as default for ComboBox behavior): when opening one of the combo that is not selected and than closing it without changing its selection - no event is triggered. BUT - this combo is under a not selected category that i want to be selected now, sincr the user thouched it. My idea was to use behavior (is in xaml code, but so far is not working...)

The code (more or less...):

<ListBox ItemsSource="{Binding Categories}">
        <ListBox.ItemTemplate>
            <DataTemplate>
                <StackPanel Orientation="Vertical">
                    <RadioButton Content="{Binding CategotyName}" GroupName="TestCategory" IsChecked="{Binding IsSelected}"
                                 cal:Message.Attach="SelectionChanged($dataContext)]"/>
                    <ComboBox cal:Message.Attach="SelectionChanged($dataContext)]" 
                              ItemsSource="{Binding TestsNamesUnderCategory}" SelectedIndex="{Binding SelectedTestInx, Mode=TwoWay}">
                        <i:Interaction.Behaviors>
                            <local:ComboBoxReSelectionBehavior />
                        </i:Interaction.Behaviors>
                    </ComboBox>
                </StackPanel>
            </DataTemplate>
        </ListBox.ItemTemplate>
    </ListBox>

the line cal:Message.Attach="SelectionChanged($dataContext)]" is using Caliburn framework, it just send the trigger to my method.

Hope this is more clear now. Thanks!

Keren
  • 407
  • 2
  • 7
  • 20

2 Answers2

4

Why are you not just binding the selection to your viewmodels properties, and then do whatever logic that is required there?

Xaml:

<...
   <ComboBox ItemsSource={Binding YourSource} SelectedItem={Binding YourSelectedItem}/>
.../>

ViewModel:

private string yourItem; // assuming we are just dealing with strings...
public String YourItem {
   get { return yourItem; }
   set {
          if( String.Equals(yourItem, value, StringComparison.OrdinalIgnoreCase) )
             return;

          OnYourItemChanged(); // Do your logics here
          RaisePropertyChanged("YourItem");
        }
   }

   private void OnYourItemChanged()
   {
       // .. do stuff here 
   }

If you absolutely need to use events use event-to-command instead...

Assuming you are using System.Windows.Interactivity & Galasoft MVVM light

References:

 xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactivity"      
 xmlns:cmd="clr-namespace:GalaSoft.MvvmLight.Command;assembly=GalaSoft.MvvmLight.Extras.WPF4"

Xaml:

<...
   <ComboBox ItemsSource={Binding YourSource} SelectedItem={Binding YourSelectedItem}>
       <i:Interaction.Triggers>
           <i:EventTrigger EventName="SelectionChanged">
               <cmd:EventToCommand Command="{Binding SomeCommand}" PassEventArgsToCommand="True" />
    </i:EventTrigger>
</i:Interaction.Triggers>
   </ComboBox>
.../>

This will hook your event up to a command, which will be executed on the viewmodel with parameters as requested.

ViewModel:

 public class YourViewModel : ViewModelBase 
 {
      public ICommand SomeCommand { get; set; }

      public YourViewModel(......)
      {
          SomeCommand = new RelayCommand<SelectionChangedEventArgs>(YourCommandMethod);
      }

      private void YourCommandMethod(SelectionChangedEventArgs e)
      {
          // Do your magic here.... 
      }
 }

Note I wrote this without any access to vs on this computer... There are plenty of examples on how to do this. Hope it helps.

Stígandr
  • 2,874
  • 21
  • 36
  • Thanks, Stian. I do exactly that. My question is on a special case, when opening the combo but not changing the selection. in this case, i want to know the combo was opened, and take the selected item (which was not changed). what missing, is the trigger when this happens. – Keren Jul 23 '14 at 12:46
  • 1
    As stated earlier you have the property IsDropDownOpen and you also have the event DropDownClosed. If I understand you correctly. Replace the event in the code above with that event, bind against your selected item, and check if it changes. – Stígandr Jul 23 '14 at 13:55
2

If you just need to trigger the event you can call the method from a command activated by DropDownClosed.

Albert Einstein
  • 7,472
  • 8
  • 36
  • 71
Hamma
  • 183
  • 1
  • 4
  • 12
  • 2
    This is exactly the quiestion... which method? – Keren Jul 23 '14 at 08:54
  • The method that you are using to handle the comboBox.SelectionChanged evet. – Hamma Jul 23 '14 at 08:58
  • Now i understand hat you mean.. but it wont fit to my project as it MVVM style, this is the reason i'm trying to do this by a behavior. – Keren Jul 23 '14 at 09:01
  • 1
    Thanks Hamma for tring to help, but you answer is a little vage.. what do you mean by a command? – Keren Jul 23 '14 at 10:11
  • My answer is vague as is your question, there is no code or anything. If you are trying to implement MVVM, you should give a look to Commands. There are a lot of tutorials out there, just google and you'll find a lot of material. A simplified implementation for commands is called RelayCommand, you could look for it as well. I am sorry my answer look vague to you, but this is not the place to find information like that; I told you what you should use, now you look at it, try it and if you have implementation issues you can ask a question with proper code. It's easier to help you that way. – Hamma Jul 23 '14 at 11:26
  • A good place to start looking could be [here](http://msdn.microsoft.com/en-us/magazine/dn237302.aspx) – Hamma Jul 23 '14 at 11:27
  • I added some code to try explain the situation, by my question is accualy a more general one: Is it possible to trigger an event of UI element from a beaviour? And if so - HOW? – Keren Jul 23 '14 at 13:12
  • See the accepted answer: https://stackoverflow.com/questions/5668815/wpf-combobox-in-datagrid-databinding-update-not-working?answertab=active#tab-top – Ahmed Ahmedov Apr 15 '18 at 20:17