Revert "File scoped namespaces"

This reverts commit d31d8f574e.
This commit is contained in:
Burak Kaan Köse
2025-02-16 11:43:30 +01:00
parent d31d8f574e
commit cf9869b71e
617 changed files with 32097 additions and 31478 deletions

View File

@@ -7,149 +7,150 @@ using Wino.Core.Domain.Entities.Calendar;
using Wino.Core.Domain.Interfaces;
using Wino.Core.Domain.Models.Calendar;
namespace Wino.Core.Domain.Collections;
public class CalendarEventCollection
namespace Wino.Core.Domain.Collections
{
public event EventHandler<ICalendarItem> CalendarItemAdded;
public event EventHandler<ICalendarItem> CalendarItemRemoved;
public event EventHandler CalendarItemsCleared;
private ObservableRangeCollection<ICalendarItem> _internalRegularEvents = [];
private ObservableRangeCollection<ICalendarItem> _internalAllDayEvents = [];
public ReadOnlyObservableCollection<ICalendarItem> RegularEvents { get; }
public ReadOnlyObservableCollection<ICalendarItem> AllDayEvents { get; } // TODO: Rename this to include multi-day events.
public ITimePeriod Period { get; }
public CalendarSettings Settings { get; }
private readonly List<ICalendarItem> _allItems = new List<ICalendarItem>();
public CalendarEventCollection(ITimePeriod period, CalendarSettings settings)
public class CalendarEventCollection
{
Period = period;
Settings = settings;
public event EventHandler<ICalendarItem> CalendarItemAdded;
public event EventHandler<ICalendarItem> CalendarItemRemoved;
RegularEvents = new ReadOnlyObservableCollection<ICalendarItem>(_internalRegularEvents);
AllDayEvents = new ReadOnlyObservableCollection<ICalendarItem>(_internalAllDayEvents);
}
public event EventHandler CalendarItemsCleared;
public bool HasCalendarEvent(AccountCalendar accountCalendar)
=> _allItems.Any(x => x.AssignedCalendar.Id == accountCalendar.Id);
private ObservableRangeCollection<ICalendarItem> _internalRegularEvents = [];
private ObservableRangeCollection<ICalendarItem> _internalAllDayEvents = [];
public ICalendarItem GetCalendarItem(Guid calendarItemId)
{
return _allItems.FirstOrDefault(x => x.Id == calendarItemId);
}
public ReadOnlyObservableCollection<ICalendarItem> RegularEvents { get; }
public ReadOnlyObservableCollection<ICalendarItem> AllDayEvents { get; } // TODO: Rename this to include multi-day events.
public ITimePeriod Period { get; }
public CalendarSettings Settings { get; }
public void ClearSelectionStates()
{
foreach (var item in _allItems)
private readonly List<ICalendarItem> _allItems = new List<ICalendarItem>();
public CalendarEventCollection(ITimePeriod period, CalendarSettings settings)
{
if (item is ICalendarItemViewModel calendarItemViewModel)
Period = period;
Settings = settings;
RegularEvents = new ReadOnlyObservableCollection<ICalendarItem>(_internalRegularEvents);
AllDayEvents = new ReadOnlyObservableCollection<ICalendarItem>(_internalAllDayEvents);
}
public bool HasCalendarEvent(AccountCalendar accountCalendar)
=> _allItems.Any(x => x.AssignedCalendar.Id == accountCalendar.Id);
public ICalendarItem GetCalendarItem(Guid calendarItemId)
{
return _allItems.FirstOrDefault(x => x.Id == calendarItemId);
}
public void ClearSelectionStates()
{
foreach (var item in _allItems)
{
calendarItemViewModel.IsSelected = false;
if (item is ICalendarItemViewModel calendarItemViewModel)
{
calendarItemViewModel.IsSelected = false;
}
}
}
}
public void FilterByCalendars(IEnumerable<Guid> visibleCalendarIds)
{
foreach (var item in _allItems)
public void FilterByCalendars(IEnumerable<Guid> visibleCalendarIds)
{
var collections = GetProperCollectionsForCalendarItem(item);
foreach (var item in _allItems)
{
var collections = GetProperCollectionsForCalendarItem(item);
foreach (var collection in collections)
{
if (!visibleCalendarIds.Contains(item.AssignedCalendar.Id) && collection.Contains(item))
{
RemoveCalendarItemInternal(collection, item, false);
}
else if (visibleCalendarIds.Contains(item.AssignedCalendar.Id) && !collection.Contains(item))
{
AddCalendarItemInternal(collection, item, false);
}
}
}
}
private IEnumerable<ObservableRangeCollection<ICalendarItem>> GetProperCollectionsForCalendarItem(ICalendarItem calendarItem)
{
// All-day events go to all days.
// Multi-day events go to both.
// Anything else goes to regular.
if (calendarItem.IsAllDayEvent)
{
return [_internalAllDayEvents];
}
else if (calendarItem.IsMultiDayEvent)
{
return [_internalRegularEvents, _internalAllDayEvents];
}
else
{
return [_internalRegularEvents];
}
}
public void AddCalendarItem(ICalendarItem calendarItem)
{
var collections = GetProperCollectionsForCalendarItem(calendarItem);
foreach (var collection in collections)
{
if (!visibleCalendarIds.Contains(item.AssignedCalendar.Id) && collection.Contains(item))
{
RemoveCalendarItemInternal(collection, item, false);
}
else if (visibleCalendarIds.Contains(item.AssignedCalendar.Id) && !collection.Contains(item))
{
AddCalendarItemInternal(collection, item, false);
}
AddCalendarItemInternal(collection, calendarItem);
}
}
}
private IEnumerable<ObservableRangeCollection<ICalendarItem>> GetProperCollectionsForCalendarItem(ICalendarItem calendarItem)
{
// All-day events go to all days.
// Multi-day events go to both.
// Anything else goes to regular.
if (calendarItem.IsAllDayEvent)
public void RemoveCalendarItem(ICalendarItem calendarItem)
{
return [_internalAllDayEvents];
}
else if (calendarItem.IsMultiDayEvent)
{
return [_internalRegularEvents, _internalAllDayEvents];
}
else
{
return [_internalRegularEvents];
}
}
var collections = GetProperCollectionsForCalendarItem(calendarItem);
public void AddCalendarItem(ICalendarItem calendarItem)
{
var collections = GetProperCollectionsForCalendarItem(calendarItem);
foreach (var collection in collections)
{
AddCalendarItemInternal(collection, calendarItem);
}
}
public void RemoveCalendarItem(ICalendarItem calendarItem)
{
var collections = GetProperCollectionsForCalendarItem(calendarItem);
foreach (var collection in collections)
{
RemoveCalendarItemInternal(collection, calendarItem);
}
}
private void AddCalendarItemInternal(ObservableRangeCollection<ICalendarItem> collection, ICalendarItem calendarItem, bool create = true)
{
if (calendarItem is not ICalendarItemViewModel)
throw new ArgumentException("CalendarItem must be of type ICalendarItemViewModel", nameof(calendarItem));
collection.Add(calendarItem);
if (create)
{
_allItems.Add(calendarItem);
foreach (var collection in collections)
{
RemoveCalendarItemInternal(collection, calendarItem);
}
}
CalendarItemAdded?.Invoke(this, calendarItem);
}
private void RemoveCalendarItemInternal(ObservableRangeCollection<ICalendarItem> collection, ICalendarItem calendarItem, bool destroy = true)
{
if (calendarItem is not ICalendarItemViewModel)
throw new ArgumentException("CalendarItem must be of type ICalendarItemViewModel", nameof(calendarItem));
collection.Remove(calendarItem);
if (destroy)
private void AddCalendarItemInternal(ObservableRangeCollection<ICalendarItem> collection, ICalendarItem calendarItem, bool create = true)
{
_allItems.Remove(calendarItem);
if (calendarItem is not ICalendarItemViewModel)
throw new ArgumentException("CalendarItem must be of type ICalendarItemViewModel", nameof(calendarItem));
collection.Add(calendarItem);
if (create)
{
_allItems.Add(calendarItem);
}
CalendarItemAdded?.Invoke(this, calendarItem);
}
CalendarItemRemoved?.Invoke(this, calendarItem);
}
private void RemoveCalendarItemInternal(ObservableRangeCollection<ICalendarItem> collection, ICalendarItem calendarItem, bool destroy = true)
{
if (calendarItem is not ICalendarItemViewModel)
throw new ArgumentException("CalendarItem must be of type ICalendarItemViewModel", nameof(calendarItem));
public void Clear()
{
_internalAllDayEvents.Clear();
_internalRegularEvents.Clear();
_allItems.Clear();
collection.Remove(calendarItem);
CalendarItemsCleared?.Invoke(this, EventArgs.Empty);
if (destroy)
{
_allItems.Remove(calendarItem);
}
CalendarItemRemoved?.Invoke(this, calendarItem);
}
public void Clear()
{
_internalAllDayEvents.Clear();
_internalRegularEvents.Clear();
_allItems.Clear();
CalendarItemsCleared?.Invoke(this, EventArgs.Empty);
}
}
}

View File

@@ -2,40 +2,41 @@
using Wino.Core.Domain.Interfaces;
using Wino.Core.Domain.Models.Calendar;
namespace Wino.Core.Domain.Collections;
public class DayRangeCollection : ObservableRangeCollection<DayRangeRenderModel>
namespace Wino.Core.Domain.Collections
{
/// <summary>
/// Gets the range of dates that are currently displayed in the collection.
/// </summary>
public DateRange DisplayRange
public class DayRangeCollection : ObservableRangeCollection<DayRangeRenderModel>
{
get
/// <summary>
/// Gets the range of dates that are currently displayed in the collection.
/// </summary>
public DateRange DisplayRange
{
if (Count == 0) return null;
get
{
if (Count == 0) return null;
var minimumLoadedDate = this[0].CalendarRenderOptions.DateRange.StartDate;
var maximumLoadedDate = this[Count - 1].CalendarRenderOptions.DateRange.EndDate;
var minimumLoadedDate = this[0].CalendarRenderOptions.DateRange.StartDate;
var maximumLoadedDate = this[Count - 1].CalendarRenderOptions.DateRange.EndDate;
return new DateRange(minimumLoadedDate, maximumLoadedDate);
return new DateRange(minimumLoadedDate, maximumLoadedDate);
}
}
}
public void RemoveCalendarItem(ICalendarItem calendarItem)
{
foreach (var dayRange in this)
public void RemoveCalendarItem(ICalendarItem calendarItem)
{
foreach (var dayRange in this)
{
}
}
}
public void AddCalendarItem(ICalendarItem calendarItem)
{
foreach (var dayRange in this)
public void AddCalendarItem(ICalendarItem calendarItem)
{
var calendarDayModel = dayRange.CalendarDays.FirstOrDefault(x => x.Period.HasInside(calendarItem.Period.Start));
calendarDayModel?.EventsCollection.AddCalendarItem(calendarItem);
foreach (var dayRange in this)
{
var calendarDayModel = dayRange.CalendarDays.FirstOrDefault(x => x.Period.HasInside(calendarItem.Period.Start));
calendarDayModel?.EventsCollection.AddCalendarItem(calendarItem);
}
}
}
}

View File

@@ -4,170 +4,171 @@ using System.Collections.ObjectModel;
using System.Collections.Specialized;
using System.ComponentModel;
namespace Wino.Core.Domain.Collections;
/// <summary>
/// Represents a dynamic data collection that provides notifications when items get added, removed, or when the whole list is refreshed.
/// </summary>
/// <typeparam name="T"></typeparam>
public class ObservableRangeCollection<T> : ObservableCollection<T>
namespace Wino.Core.Domain.Collections
{
/// <summary>
/// Initializes a new instance of the System.Collections.ObjectModel.ObservableCollection(Of T) class.
/// Represents a dynamic data collection that provides notifications when items get added, removed, or when the whole list is refreshed.
/// </summary>
public ObservableRangeCollection()
: base()
/// <typeparam name="T"></typeparam>
public class ObservableRangeCollection<T> : ObservableCollection<T>
{
}
/// <summary>
/// Initializes a new instance of the System.Collections.ObjectModel.ObservableCollection(Of T) class that contains elements copied from the specified collection.
/// </summary>
/// <param name="collection">collection: The collection from which the elements are copied.</param>
/// <exception cref="ArgumentNullException">The collection parameter cannot be null.</exception>
public ObservableRangeCollection(IEnumerable<T> collection)
: base(collection)
{
}
/// <summary>
/// Adds the elements of the specified collection to the end of the ObservableCollection(Of T).
/// </summary>
public void AddRange(IEnumerable<T> collection, NotifyCollectionChangedAction notificationMode = NotifyCollectionChangedAction.Add)
{
if (notificationMode != NotifyCollectionChangedAction.Add && notificationMode != NotifyCollectionChangedAction.Reset)
throw new ArgumentException("Mode must be either Add or Reset for AddRange.", nameof(notificationMode));
if (collection == null)
throw new ArgumentNullException(nameof(collection));
CheckReentrancy();
var startIndex = Count;
var itemsAdded = AddArrangeCore(collection);
if (!itemsAdded)
return;
if (notificationMode == NotifyCollectionChangedAction.Reset)
/// <summary>
/// Initializes a new instance of the System.Collections.ObjectModel.ObservableCollection(Of T) class.
/// </summary>
public ObservableRangeCollection()
: base()
{
RaiseChangeNotificationEvents(action: NotifyCollectionChangedAction.Reset);
return;
}
var changedItems = collection is List<T> ? (List<T>)collection : new List<T>(collection);
RaiseChangeNotificationEvents(
action: NotifyCollectionChangedAction.Add,
changedItems: changedItems,
startingIndex: startIndex);
}
/// <summary>
/// Removes the first occurence of each item in the specified collection from ObservableCollection(Of T). NOTE: with notificationMode = Remove, removed items starting index is not set because items are not guaranteed to be consecutive.
/// </summary>
public void RemoveRange(IEnumerable<T> collection, NotifyCollectionChangedAction notificationMode = NotifyCollectionChangedAction.Reset)
{
if (notificationMode != NotifyCollectionChangedAction.Remove && notificationMode != NotifyCollectionChangedAction.Reset)
throw new ArgumentException("Mode must be either Remove or Reset for RemoveRange.", nameof(notificationMode));
if (collection == null)
throw new ArgumentNullException(nameof(collection));
CheckReentrancy();
if (notificationMode == NotifyCollectionChangedAction.Reset)
/// <summary>
/// Initializes a new instance of the System.Collections.ObjectModel.ObservableCollection(Of T) class that contains elements copied from the specified collection.
/// </summary>
/// <param name="collection">collection: The collection from which the elements are copied.</param>
/// <exception cref="ArgumentNullException">The collection parameter cannot be null.</exception>
public ObservableRangeCollection(IEnumerable<T> collection)
: base(collection)
{
var raiseEvents = false;
foreach (var item in collection)
{
Items.Remove(item);
raiseEvents = true;
}
}
if (raiseEvents)
/// <summary>
/// Adds the elements of the specified collection to the end of the ObservableCollection(Of T).
/// </summary>
public void AddRange(IEnumerable<T> collection, NotifyCollectionChangedAction notificationMode = NotifyCollectionChangedAction.Add)
{
if (notificationMode != NotifyCollectionChangedAction.Add && notificationMode != NotifyCollectionChangedAction.Reset)
throw new ArgumentException("Mode must be either Add or Reset for AddRange.", nameof(notificationMode));
if (collection == null)
throw new ArgumentNullException(nameof(collection));
CheckReentrancy();
var startIndex = Count;
var itemsAdded = AddArrangeCore(collection);
if (!itemsAdded)
return;
if (notificationMode == NotifyCollectionChangedAction.Reset)
{
RaiseChangeNotificationEvents(action: NotifyCollectionChangedAction.Reset);
return;
}
var changedItems = new List<T>(collection);
for (var i = 0; i < changedItems.Count; i++)
{
if (!Items.Remove(changedItems[i]))
{
changedItems.RemoveAt(i); //Can't use a foreach because changedItems is intended to be (carefully) modified
i--;
return;
}
var changedItems = collection is List<T> ? (List<T>)collection : new List<T>(collection);
RaiseChangeNotificationEvents(
action: NotifyCollectionChangedAction.Add,
changedItems: changedItems,
startingIndex: startIndex);
}
if (changedItems.Count == 0)
return;
RaiseChangeNotificationEvents(
action: NotifyCollectionChangedAction.Remove,
changedItems: changedItems);
}
/// <summary>
/// Clears the current collection and replaces it with the specified item.
/// </summary>
public void Replace(T item) => ReplaceRange(new T[] { item });
/// <summary>
/// Clears the current collection and replaces it with the specified collection.
/// </summary>
public void ReplaceRange(IEnumerable<T> collection)
{
if (collection == null)
throw new ArgumentNullException(nameof(collection));
CheckReentrancy();
var previouslyEmpty = Items.Count == 0;
Items.Clear();
AddArrangeCore(collection);
var currentlyEmpty = Items.Count == 0;
if (previouslyEmpty && currentlyEmpty)
return;
RaiseChangeNotificationEvents(action: NotifyCollectionChangedAction.Reset);
}
public void InsertRange(IEnumerable<T> items)
{
CheckReentrancy();
foreach (var item in items)
Items.Insert(0, item);
OnCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Reset));
}
private bool AddArrangeCore(IEnumerable<T> collection)
{
var itemAdded = false;
foreach (var item in collection)
/// <summary>
/// Removes the first occurence of each item in the specified collection from ObservableCollection(Of T). NOTE: with notificationMode = Remove, removed items starting index is not set because items are not guaranteed to be consecutive.
/// </summary>
public void RemoveRange(IEnumerable<T> collection, NotifyCollectionChangedAction notificationMode = NotifyCollectionChangedAction.Reset)
{
Items.Add(item);
itemAdded = true;
if (notificationMode != NotifyCollectionChangedAction.Remove && notificationMode != NotifyCollectionChangedAction.Reset)
throw new ArgumentException("Mode must be either Remove or Reset for RemoveRange.", nameof(notificationMode));
if (collection == null)
throw new ArgumentNullException(nameof(collection));
CheckReentrancy();
if (notificationMode == NotifyCollectionChangedAction.Reset)
{
var raiseEvents = false;
foreach (var item in collection)
{
Items.Remove(item);
raiseEvents = true;
}
if (raiseEvents)
RaiseChangeNotificationEvents(action: NotifyCollectionChangedAction.Reset);
return;
}
var changedItems = new List<T>(collection);
for (var i = 0; i < changedItems.Count; i++)
{
if (!Items.Remove(changedItems[i]))
{
changedItems.RemoveAt(i); //Can't use a foreach because changedItems is intended to be (carefully) modified
i--;
}
}
if (changedItems.Count == 0)
return;
RaiseChangeNotificationEvents(
action: NotifyCollectionChangedAction.Remove,
changedItems: changedItems);
}
return itemAdded;
}
private void RaiseChangeNotificationEvents(NotifyCollectionChangedAction action, List<T> changedItems = null, int startingIndex = -1)
{
OnPropertyChanged(new PropertyChangedEventArgs(nameof(Count)));
OnPropertyChanged(new PropertyChangedEventArgs("Item[]"));
/// <summary>
/// Clears the current collection and replaces it with the specified item.
/// </summary>
public void Replace(T item) => ReplaceRange(new T[] { item });
if (changedItems is null)
OnCollectionChanged(new NotifyCollectionChangedEventArgs(action));
else
OnCollectionChanged(new NotifyCollectionChangedEventArgs(action, changedItems: changedItems, startingIndex: startingIndex));
/// <summary>
/// Clears the current collection and replaces it with the specified collection.
/// </summary>
public void ReplaceRange(IEnumerable<T> collection)
{
if (collection == null)
throw new ArgumentNullException(nameof(collection));
CheckReentrancy();
var previouslyEmpty = Items.Count == 0;
Items.Clear();
AddArrangeCore(collection);
var currentlyEmpty = Items.Count == 0;
if (previouslyEmpty && currentlyEmpty)
return;
RaiseChangeNotificationEvents(action: NotifyCollectionChangedAction.Reset);
}
public void InsertRange(IEnumerable<T> items)
{
CheckReentrancy();
foreach (var item in items)
Items.Insert(0, item);
OnCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Reset));
}
private bool AddArrangeCore(IEnumerable<T> collection)
{
var itemAdded = false;
foreach (var item in collection)
{
Items.Add(item);
itemAdded = true;
}
return itemAdded;
}
private void RaiseChangeNotificationEvents(NotifyCollectionChangedAction action, List<T> changedItems = null, int startingIndex = -1)
{
OnPropertyChanged(new PropertyChangedEventArgs(nameof(Count)));
OnPropertyChanged(new PropertyChangedEventArgs("Item[]"));
if (changedItems is null)
OnCollectionChanged(new NotifyCollectionChangedEventArgs(action));
else
OnCollectionChanged(new NotifyCollectionChangedEventArgs(action, changedItems: changedItems, startingIndex: startingIndex));
}
}
}