/// <summary> /// Recycles this instance of the <see cref="CollectionChangedEventArgs{T}"/> class. /// </summary> /// <remarks> /// <para> /// This method resets this instance and returns it to a resource pool if resource pooling is /// enabled (see <see cref="ResourcePool.Enabled">ResourcePool.Enabled</see>). /// </para> /// </remarks> public void Recycle() { Action = CollectionChangedAction.Add; NewItemsIndex = -1; NewItems.Clear(); OldItemsIndex = -1; OldItems.Clear(); Pool.Recycle(this); }
/// <summary> /// Update the container buffer and item snapshots. Old (removed) items will be added to /// <see cref="OldItems"/> and new items to <see cref="NewItems"/>. /// </summary> public void Update() { _container.TakeSnapshot(); _previousSegments = _currentSegments; if (_previousData.Length != _currentData.Length) { Array.Resize(ref _previousData, _currentData.Length); } Buffer.BlockCopy(_currentData, 0, _previousData, 0, _currentData.Length); _currentSegments = _container.GetAllocatedBytes(ref _currentData); if (_currentData.Length != _previousData.Length) // buffer was resized (and replaced), update underlying buffer for all items { for (int i = 0; i < _items.Length; i++) { if (_items[i] == null) { continue; } _items[i].SetSnapshot(_currentData, i * _container.ItemSize, _container.ItemSize); } } if (_previousMapping.Length != _currentMapping.Length) { Array.Resize(ref _previousMapping, _currentMapping.Length); } Buffer.BlockCopy(_currentMapping, 0, _previousMapping, 0, _currentMapping.Length * sizeof(int)); var count = _currentData.Length / _container.ItemSize; var mr = new BufferMemoryReader(_currentData); if (_currentMapping.Length != count) { Array.Resize(ref _currentMapping, count); } for (int i = 0; i <= _container.MaxIndex; i++) { _currentMapping[i] = mr.Read <int>(i * _container.ItemSize); } for (int i = _container.MaxIndex + 1; i < count; i++) { _currentMapping[i] = -1; } NewItems.Clear(); OldItems.Clear(); if (_items.Length != _container.Capacity) { Array.Resize(ref _items, _container.Capacity); } // Compare against previous where there is a value. for (int i = 0; i < Math.Min(_previousMapping.Length, _currentMapping.Length); i++) { if (_currentMapping[i] != _previousMapping[i]) { if (_previousMapping[i] != -1) { var item = CreatePreviousItem(i); OnItemRemoved(i, item); OldItems.Add(item); } if (_currentMapping[i] != -1 && _currentMapping[i] != 0) // NB: New item starts with ID 0 { var item = CreateCurrentItem(i); OnItemAdded(i, item); NewItems.Add(item); } } } // Check expanded area. for (int i = _previousMapping.Length; i < _currentMapping.Length; i++) { if (_currentMapping[i] != -1) { var item = CreateCurrentItem(i); OnItemAdded(i, item); NewItems.Add(item); } } // Check reduced area. for (int i = _currentMapping.Length; i < _previousMapping.Length; i++) { if (_previousMapping[i] != -1) { var item = CreatePreviousItem(i); OnItemRemoved(i, item); OldItems.Add(item); } } }
private void ClearChanges() { NewItems.Clear(); DirtyItems.Clear(); DeletedItems.Clear(); }