示例#1
0
        void RefreshSelectedItems(NotifyCollectionChangedEventArgs e)
        {
            if (e.Action == NotifyCollectionChangedAction.Reset)
            {
                UnselectAllItems();
            }
            if (e.OldItems != null)
            {
                List <object> oldItems = INTERNAL_ListsHelper.ConvertToListOfObjectsOrNull(e.OldItems);
                foreach (object item in oldItems)
                {
                    SetItemVisualSelectionState(item, false);
                }
            }
            if (e.NewItems != null)
            {
                List <object> newItems = INTERNAL_ListsHelper.ConvertToListOfObjectsOrNull(e.NewItems);
                foreach (object item in newItems)
                {
                    SetItemVisualSelectionState(item, true);
                }
            }
            // Update the SelectedItem property:
            // based on WPF's behaviour, SelectedItem is the item that was first selected among the currently selected items:
            IList items = SelectedItems; //Note: items cannot be null as we came here as a result of it firing the CollectionChanged event.

            if (items.Count > 0)
            {
                bool tempSkipSelectionChangedEvent = _skipSelectionChangedEvent;
                _skipSelectionChangedEvent = true; //setting this to true so setting SelectedItem will not remove the items from the list.

                foreach (object item in items)     //Note: items being an IList, we do not have access to ElementAt ot First so we do this.
                {
                    if (SelectedItem != item)
                    {
                        SelectedItem = item;
                    }
                    break;
                }
                _skipSelectionChangedEvent = tempSkipSelectionChangedEvent;
            } //todo: should we unset SelectedItem when the user clears SelectedItems? (in that case, do not do it if _isIntermediarySelectedItemChange is true)

            if (!_skipSelectionChangedEvent)
            {
                //Fire the SelectionChanged event:
                var removedItems = e.OldItems ?? new Collection <object>();
                var addedItems   = e.NewItems ?? new Collection <object>();
                Dispatcher.BeginInvoke(() => //Note: We need to delay firing the event so we're done with everything we need to do in case the user tries to modify the selection.
                {
                    OnSelectionChanged(new SelectionChangedEventArgs(removedItems, addedItems));
                });
            }
        }
示例#2
0
        void RefreshSelectedItems(NotifyCollectionChangedEventArgs e)
        {
            if (e.Action == NotifyCollectionChangedAction.Reset)
            {
                UnselectAllItems();
            }
            if (e.OldItems != null)
            {
                List <object> oldItems = INTERNAL_ListsHelper.ConvertToListOfObjectsOrNull(e.OldItems);
                foreach (object item in oldItems)
                {
                    SetItemVisualSelectionState(item, false);
                }
            }
            if (e.NewItems != null)
            {
                List <object> newItems = INTERNAL_ListsHelper.ConvertToListOfObjectsOrNull(e.NewItems);
                foreach (object item in newItems)
                {
                    SetItemVisualSelectionState(item, true);
                }
            }
            // Update the SelectedItem property:
            // based on WPF's behaviour, SelectedItem is the item that was first selected among the currently selected items:
            IList items = SelectedItems; //Note: items cannot be null as we came here as a result of it firing the CollectionChanged event.

            if (items.Count > 0)
            {
                foreach (object item in items) //Note: items being an IList, we do not have access to ElementAt ot First so we do this.
                {
                    SelectedItem = item;
                    break;
                }
            }

            //Fire the SelectionChanged event:
            var removedItems = e.OldItems ?? new Collection <object>();
            var addedItems   = e.NewItems ?? new Collection <object>();

            OnSelectionChanged(new SelectionChangedEventArgs(removedItems, addedItems));
        }
示例#3
0
 void RefreshSelectedItems(NotifyCollectionChangedEventArgs e)
 {
     if (e.Action == NotifyCollectionChangedAction.Reset)
     {
         UnselectAllItems();
     }
     if (e.OldItems != null)
     {
         List <object> oldItems = INTERNAL_ListsHelper.ConvertToListOfObjectsOrNull(e.OldItems);
         foreach (object item in oldItems)
         {
             SetItemVisualSelectionState(item, false);
         }
     }
     if (e.NewItems != null)
     {
         List <object> newItems = INTERNAL_ListsHelper.ConvertToListOfObjectsOrNull(e.NewItems);
         foreach (object item in newItems)
         {
             SetItemVisualSelectionState(item, true);
         }
     }
 }
示例#4
0
        void listBoxItem_Click(object sender, RoutedEventArgs e)
        {
#if MIGRATION
            ModifierKeys modifiersKey = new ModifierKeys();
            modifiersKey = Keyboard.Modifiers;
            bool isControl = modifiersKey.HasFlag(ModifierKeys.Control);
            bool isShift   = modifiersKey.HasFlag(ModifierKeys.Shift);
#else
            VirtualKeyModifiers modifiersKey = new VirtualKeyModifiers();
            modifiersKey = Keyboard.Modifiers;
            bool isControl = modifiersKey.HasFlag(VirtualKeyModifiers.Control);
            bool isShift   = modifiersKey.HasFlag(VirtualKeyModifiers.Shift);
#endif
            SelectorItem selectorItem = (SelectorItem)sender;
            //---------------------------------------------------
            //Single
            //---------------------------------------------------
            if (SelectionMode == SelectionMode.Single)
            {
                INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Clear(SelectedItems);
                SelectedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
            }
            //---------------------------------------------------
            //Multiple
            //---------------------------------------------------
            else if (SelectionMode == SelectionMode.Multiple)
            {
                //If click on an already selected element
                if (INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Contains(SelectedItems, selectorItem.INTERNAL_CorrespondingItem))//if we are in a multiple mode and the currently selected element is the one we clicked, we want to unselect it.
                {
                    INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Remove(SelectedItems, selectorItem.INTERNAL_CorrespondingItem);
                }
                //else  click on a new element
                else
                {
                    SelectedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
                }
            }
            //---------------------------------------------------
            //Extended
            //---------------------------------------------------
            else if (SelectionMode == SelectionMode.Extended)
            {
                int indexOfClickedItem = INTERNAL_ListsHelper.ConvertToListOfObjectsOrNull(Items).IndexOf(selectorItem.INTERNAL_CorrespondingItem); //todo-perfs: this is O(N).

                //if Shift is pressed
                if (isShift)
                {
                    int indexStart = _indexOfLastClickedItemWithoutShiftKey;
                    int indexEnd   = indexOfClickedItem;
                    int change;
                    if (indexStart > indexEnd)
                    {
                        change     = indexEnd;
                        indexEnd   = indexStart;
                        indexStart = change;
                    }
                    int index = 0;
                    //clear before adding
                    INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Clear(SelectedItems);
                    foreach (object item in Items)
                    {
                        if (indexStart <= index && index <= indexEnd)
                        {
                            if (!INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Contains(SelectedItems, item)) //todo-perfs: use a dictionary
                            {
                                SelectedItems.Add(item);
                            }
                        }
                        index++;
                    }
                }
                //if Control is pressed
                else if (isControl)
                {
                    //If click on an already selected element
                    if (INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Contains(SelectedItems, selectorItem.INTERNAL_CorrespondingItem))//if we are in a multiple mode and the currently selected element is the one we clicked, we want to unselect it.
                    {
                        INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Remove(SelectedItems, selectorItem.INTERNAL_CorrespondingItem);
                    }
                    //else click on a new element
                    else
                    {
                        SelectedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
                    }
                }
                //Nothing is pressed
                else
                {
                    INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Clear(SelectedItems);
                    SelectedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
                }

                if (!isShift)
                {
                    _indexOfLastClickedItemWithoutShiftKey = indexOfClickedItem;
                }
            }
            else
            {
                throw new NotSupportedException("SelectionMode is not Single, Multiple or Extended.");
            }
        }
示例#5
0
        void listBoxItem_Click(object sender, RoutedEventArgs e)
        {
            _skipSelectionChangedEvent = true; // Note: we keep this to true for the whole method since this method will handle the SelectionChanged event itself (this way we don't risk having multiple calls to SelectionChanged when adding multiple elements for example).

            //object[] oldItems = null;
            bool hasSelectionChanged = false;

            List <object> addedItems   = new List <object>();
            List <object> removedItems = new List <object>();

#if MIGRATION
            ModifierKeys modifiersKey = new ModifierKeys();
            modifiersKey = Keyboard.Modifiers;
            bool isControl = modifiersKey.HasFlag(ModifierKeys.Control);
            bool isShift   = modifiersKey.HasFlag(ModifierKeys.Shift);
#else
            VirtualKeyModifiers modifiersKey = new VirtualKeyModifiers();
            modifiersKey = Keyboard.Modifiers;
            bool isControl = modifiersKey.HasFlag(VirtualKeyModifiers.Control);
            bool isShift   = modifiersKey.HasFlag(VirtualKeyModifiers.Shift);
#endif
            SelectorItem selectorItem = (SelectorItem)sender;
            //---------------------------------------------------
            //Single
            //---------------------------------------------------
            if (SelectionMode == SelectionMode.Single)
            {
                if (SelectedItem != selectorItem.INTERNAL_CorrespondingItem) //todo: SelectedItems contains more than one element (I'm pretty sure we ignore is as long as the clicked element is the SelectedItem).
                {
                    HashSet <object> selectedItemsHashSet = CopyToHashSet(SelectedItems);
                    INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Clear(SelectedItems);
                    SelectedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
                    addedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
                    if (selectedItemsHashSet.Contains(selectorItem.INTERNAL_CorrespondingItem))
                    {
                        selectedItemsHashSet.Remove(selectorItem.INTERNAL_CorrespondingItem);
                    }
                    foreach (object item in selectedItemsHashSet)
                    {
                        removedItems.Add(item);
                    }
                    hasSelectionChanged = true;
                }
            }
            //---------------------------------------------------
            //Multiple
            //---------------------------------------------------
            else if (SelectionMode == SelectionMode.Multiple)
            {
                //If click on an already selected element
                if (INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Contains(SelectedItems, selectorItem.INTERNAL_CorrespondingItem))//if we are in a multiple mode and the currently selected element is the one we clicked, we want to unselect it.
                {
                    INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Remove(SelectedItems, selectorItem.INTERNAL_CorrespondingItem);
                    removedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
                }
                //else  click on a new element
                else
                {
                    SelectedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
                    addedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
                }
                hasSelectionChanged = true;
            }
            //---------------------------------------------------
            //Extended
            //---------------------------------------------------
            else if (SelectionMode == SelectionMode.Extended)
            {
                int indexOfClickedItem = INTERNAL_ListsHelper.ConvertToListOfObjectsOrNull(Items).IndexOf(selectorItem.INTERNAL_CorrespondingItem); //todo-perfs: this is O(N).

                //if Shift is pressed
                if (isShift)
                {
                    int indexStart = _indexOfLastClickedItemWithoutShiftKey;
                    int indexEnd   = indexOfClickedItem;
                    int change;
                    if (indexStart > indexEnd)
                    {
                        change     = indexEnd;
                        indexEnd   = indexStart;
                        indexStart = change;
                    }
                    int index = 0;
                    //copy the SelectedItems in a hashset so we can easily know which items have been removed:
                    HashSet <object> selectedItemsHashSet = CopyToHashSet(SelectedItems);
                    //clear before adding
                    INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Clear(SelectedItems);
                    foreach (object item in Items)
                    {
                        if (indexStart <= index && index <= indexEnd)
                        {
                            if (!INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Contains(SelectedItems, item)) //todo-perfs: use a dictionary
                            {
                                SelectedItems.Add(item);
                                addedItems.Add(item);
                                if (selectedItemsHashSet.Contains(item))
                                {
                                    selectedItemsHashSet.Remove(item);
                                }
                            }
                        }
                        index++;
                    }
                    foreach (object item in selectedItemsHashSet)
                    {
                        removedItems.Add(item);
                    }

                    hasSelectionChanged = removedItems.Count > 0 || addedItems.Count > 0;
                }
                //if Control is pressed
                else if (isControl)
                {
                    //If click on an already selected element
                    if (INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Contains(SelectedItems, selectorItem.INTERNAL_CorrespondingItem))//if we are in a multiple mode and the currently selected element is the one we clicked, we want to unselect it.
                    {
                        INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Remove(SelectedItems, selectorItem.INTERNAL_CorrespondingItem);
                        removedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
                    }
                    //else click on a new element
                    else
                    {
                        SelectedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
                        addedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
                    }
                    hasSelectionChanged = true;
                }
                //Nothing is pressed
                else
                {
                    if (SelectedItem != selectorItem.INTERNAL_CorrespondingItem)
                    {
                        HashSet <object> selectedItemsHashSet = CopyToHashSet(SelectedItems);
                        INTERNAL_WorkaroundObservableCollectionBugWithJSIL.Clear(SelectedItems);
                        SelectedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
                        addedItems.Add(selectorItem.INTERNAL_CorrespondingItem);
                        if (selectedItemsHashSet.Contains(selectorItem.INTERNAL_CorrespondingItem))
                        {
                            selectedItemsHashSet.Remove(selectorItem.INTERNAL_CorrespondingItem);
                        }
                        foreach (object item in selectedItemsHashSet)
                        {
                            removedItems.Add(item);
                        }
                        hasSelectionChanged = true;
                    }
                }

                if (!isShift)
                {
                    _indexOfLastClickedItemWithoutShiftKey = indexOfClickedItem;
                }
            }
            else
            {
                throw new NotSupportedException("SelectionMode is not Single, Multiple or Extended.");
            }

            OnSelectionChanged(new SelectionChangedEventArgs(removedItems, addedItems));
            _skipSelectionChangedEvent = false;
        }