/// <summary> /// Replaces elements of <see cref="NavigableCollection{T, TMetadata}"/> with the elements in the specified sequence. /// </summary> /// <param name="source">The sequence of replacement elements.</param> public void Recompose(IEnumerable <Lazy <T, TMetadata> > source) { Requires.NotNull(source, nameof(source)); Lazy <T, TMetadata>[] array = source.ToArray(); using (Recomposition recomposition = new Recomposition(this)) { if (collection.Count > 0) { collection.Clear(); } for (int i = 0; i < array.Length; i++) { collection.Add(array[i]); } if (current != UnsetTuple) { T obj = current.Item1; foreach (Lazy <T, TMetadata> item in collection) { if (item != null) { TMetadata metadata = item.Metadata; if (metadata != null && metadata.Route == current.Item2 && ReferenceEquals(item.Value, obj)) { return; } } } current = UnsetTuple; if (obj != null) { recomposition.Dispose(); OnCurrentChanged(); OnPropertyChanged(CurrentPropertyChanged); NavigatedFrom(obj); } } } }
/// <summary> /// Synchronizes the <see cref="RecomposableCollection{T}"/> with the elements in the specified sequence. /// </summary> /// <param name="source">The sequence of replacement elements.</param> public void Recompose(IEnumerable <T> source) { Requires.NotNull(source, nameof(source)); T[] array = source.ToArray(); using (Recomposition recomposition = new Recomposition(this)) { if (array.Length == 0) { if (collection.Count > 0) { T[] items = collection.ToArray(); collection.Clear(); recomposition.Dispose(); OnRecomposed(new RecomposedEventArgs <T>(Array.Empty <T>(), Array.AsReadOnly(items))); } return; } List <T> list = new List <T>(array); List <int> indexes = new List <int>(); for (int i = 0; i < collection.Count; i++) { if (list.Count > 0) { int index = list.IndexOf(collection[i], comparer); if (index < 0) { indexes.Add(i); continue; } list.RemoveAt(index); continue; } indexes.Add(i); } if (indexes.Count == collection.Count) { T[] items = Array.Empty <T>(); if (collection.Count > 0) { items = collection.ToArray(); collection.Clear(); } for (int i = 0; i < array.Length; i++) { collection.Add(array[i]); } recomposition.Dispose(); OnRecomposed(new RecomposedEventArgs <T>(Array.AsReadOnly(array), Array.AsReadOnly(items))); return; } List <T> added = new List <T>(); List <T> removed = new List <T>(); for (int i = indexes.Count - 1; i >= 0; i--) { T item = collection[indexes[i]]; collection.RemoveAt(indexes[i]); removed.Insert(0, item); } for (int i = 0; i < array.Length; i++) { if (i < collection.Count) { if (comparer.Equals(array[i], collection[i])) { continue; } if (i < collection.Count - 1) { int index = collection.IndexOf(array[i], i + 1, comparer); if (index > 0) { collection.Move(index, i); continue; } } collection.Insert(i, array[i]); added.Add(array[i]); continue; } collection.Add(array[i]); added.Add(array[i]); } while (collection.Count > array.Length) { T item = collection[array.Length]; collection.RemoveAt(array.Length); removed.Add(item); } if (added.Count > 0 || removed.Count > 0) { recomposition.Dispose(); OnRecomposed(new RecomposedEventArgs <T>(added.AsReadOnly(), removed.AsReadOnly())); } } }