Refactored the calendar synchronization code using AI.

This commit is contained in:
Burak Kaan Köse
2025-07-06 17:25:38 +02:00
parent 3e889d8c08
commit 1ee0063b62
30 changed files with 3125 additions and 1086 deletions

View File

@@ -69,7 +69,7 @@
VerticalAlignment="Top"
Orientation="Horizontal"
Spacing="6">
<controls:WinoFontIcon
<!--<controls:WinoFontIcon
FontSize="12"
Foreground="{x:Bind helpers:XamlHelpers.GetReadableTextColor(CalendarItem.AssignedCalendar.BackgroundColorHex), Mode=OneWay}"
Icon="CalendarEventRepeat"
@@ -79,7 +79,7 @@
FontSize="12"
Foreground="{x:Bind helpers:XamlHelpers.GetReadableTextColor(CalendarItem.AssignedCalendar.BackgroundColorHex), Mode=OneWay}"
Icon="CalendarEventMuiltiDay"
Visibility="{x:Bind CalendarItem.IsMultiDayEvent, Mode=OneWay}" />
Visibility="{x:Bind CalendarItem.IsMultiDayEvent, Mode=OneWay}" />-->
</StackPanel>
<VisualStateManager.VisualStateGroups>

View File

@@ -7,6 +7,7 @@ using Windows.UI.Xaml.Input;
using Wino.Calendar.ViewModels.Data;
using Wino.Calendar.ViewModels.Messages;
using Wino.Core.Domain;
using Wino.Core.Domain.Enums;
using Wino.Core.Domain.Models.Calendar;
namespace Wino.Calendar.Controls;
@@ -90,7 +91,9 @@ public sealed partial class CalendarItemControl : UserControl
if (CalendarItem == null) return;
if (DisplayingDate == null) return;
if (CalendarItem.IsMultiDayEvent)
bool isMultiDayEvent = CalendarItem.CalendarItem.ItemType == CalendarItemType.MultiDay || CalendarItem.CalendarItem.ItemType == CalendarItemType.MultiDayAllDay;
if (isMultiDayEvent)
{
// Multi day events are divided into 3 categories:
// 1. All day events
@@ -103,14 +106,14 @@ public sealed partial class CalendarItemControl : UserControl
periodRelation == PeriodRelation.EnclosingStartTouching)
{
// hour -> title
CalendarItemTitle = $"{DisplayingDate.CalendarRenderOptions.CalendarSettings.GetTimeString(CalendarItem.StartDate.TimeOfDay)} -> {CalendarItem.Title}";
CalendarItemTitle = $"{DisplayingDate.CalendarRenderOptions.CalendarSettings.GetTimeString(CalendarItem.StartDateTime.TimeOfDay)} -> {CalendarItem.Title}";
}
else if (
periodRelation == PeriodRelation.EndInside ||
periodRelation == PeriodRelation.EnclosingEndTouching)
{
// title <- hour
CalendarItemTitle = $"{CalendarItem.Title} <- {DisplayingDate.CalendarRenderOptions.CalendarSettings.GetTimeString(CalendarItem.EndDate.TimeOfDay)}";
CalendarItemTitle = $"{CalendarItem.Title} <- {DisplayingDate.CalendarRenderOptions.CalendarSettings.GetTimeString(CalendarItem.EndDateTime.TimeOfDay)}";
}
else if (periodRelation == PeriodRelation.Enclosing)
{
@@ -139,11 +142,11 @@ public sealed partial class CalendarItemControl : UserControl
{
if (CalendarItem == null) return;
if (CalendarItem.IsAllDayEvent)
if (CalendarItem.CalendarItem.ItemType == CalendarItemType.AllDay)
{
VisualStateManager.GoToState(this, "AllDayEvent", true);
}
else if (CalendarItem.IsMultiDayEvent)
else if (CalendarItem.CalendarItem.ItemType == CalendarItemType.MultiDayAllDay || CalendarItem.CalendarItem.ItemType == CalendarItemType.MultiDay)
{
if (IsCustomEventArea)
{

View File

@@ -9,6 +9,7 @@ using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;
using Wino.Calendar.Models;
using Wino.Calendar.ViewModels.Data;
using Wino.Core.Domain.Enums;
using Wino.Core.Domain.Interfaces;
namespace Wino.Calendar.Controls;
@@ -46,7 +47,7 @@ public partial class WinoCalendarPanel : Panel
private double GetChildTopMargin(ICalendarItem calendarItemViewModel, double availableHeight)
{
var childStart = calendarItemViewModel.StartDate;
var childStart = calendarItemViewModel.StartDateTime;
if (childStart <= Period.Start)
{
@@ -71,7 +72,7 @@ public partial class WinoCalendarPanel : Panel
private double GetChildHeight(ICalendarItem child)
{
// All day events are not measured.
if (child.IsAllDayEvent) return 0;
if (child.ItemType == CalendarItemType.AllDay) return 0;
double childDurationInMinutes = 0d;
double availableHeight = HourHeight * 24;
@@ -80,7 +81,7 @@ public partial class WinoCalendarPanel : Panel
// Debug.WriteLine($"Render relation of {child.Title} ({child.Period.Start} - {child.Period.End}) is {periodRelation} with {Period.Start.Day}");
if (!child.IsMultiDayEvent)
if (child.ItemType != CalendarItemType.MultiDay || child.ItemType != CalendarItemType.MultiDayAllDay)
{
childDurationInMinutes = child.Period.Duration.TotalMinutes;
}
@@ -160,7 +161,7 @@ public partial class WinoCalendarPanel : Panel
double extraRightMargin = 0;
// Multi-day events don't have any margin and their hit test is disabled.
if (!child.IsMultiDayEvent)
if (child.ItemType != CalendarItemType.MultiDay || child.ItemType != CalendarItemType.MultiDayAllDay)
{
// Max of 5% of the width or 20px max.
extraRightMargin = isHorizontallyLastItem ? Math.Max(LastItemRightExtraMargin, finalSize.Width * 5 / 100) : 0;
@@ -168,8 +169,10 @@ public partial class WinoCalendarPanel : Panel
if (childWidth < 0) childWidth = 1;
bool isAllOrMultiDayEvent = child.ItemType == CalendarItemType.AllDay || child.ItemType == CalendarItemType.MultiDay || child.ItemType == CalendarItemType.MultiDayAllDay;
// Regular events must have 2px margin
if (!child.IsMultiDayEvent && !child.IsAllDayEvent)
if (!isAllOrMultiDayEvent)
{
childLeft += 2;
childTop += 2;
@@ -211,10 +214,12 @@ public partial class WinoCalendarPanel : Panel
var columns = new List<List<ICalendarItem>>();
DateTime? lastEventEnding = null;
foreach (var ev in events.OrderBy(ev => ev.StartDate).ThenBy(ev => ev.EndDate))
foreach (var ev in events.OrderBy(ev => ev.StartDateTime).ThenBy(ev => ev.EndDateTime))
{
// Multi-day events are not measured.
if (ev.IsMultiDayEvent) continue;
bool isMultiDayEvent = ev.ItemType == CalendarItemType.MultiDay || ev.ItemType == CalendarItemType.MultiDayAllDay;
if (isMultiDayEvent) continue;
if (ev.Period.Start >= lastEventEnding)
{

View File

@@ -22,6 +22,7 @@ public static class CalendarXamlHelpers
/// </summary>
public static string GetEventDetailsDateString(CalendarItemViewModel calendarItemViewModel, CalendarSettings settings)
{
// TODO: This is not correct.
if (calendarItemViewModel == null || settings == null) return string.Empty;
var start = calendarItemViewModel.Period.Start;
@@ -30,7 +31,7 @@ public static class CalendarXamlHelpers
string timeFormat = settings.DayHeaderDisplayType == DayHeaderDisplayType.TwelveHour ? "h:mm tt" : "HH:mm";
string dateFormat = settings.DayHeaderDisplayType == DayHeaderDisplayType.TwelveHour ? "dddd, dd MMMM h:mm tt" : "dddd, dd MMMM HH:mm";
if (calendarItemViewModel.IsMultiDayEvent)
if (calendarItemViewModel.CalendarItem.ItemType == CalendarItemType.MultiDay || calendarItemViewModel.CalendarItem.ItemType == CalendarItemType.MultiDayAllDay)
{
return $"{start.ToString($"dd MMMM ddd {timeFormat}", settings.CultureInfo)} - {end.ToString($"dd MMMM ddd {timeFormat}", settings.CultureInfo)}";
}
@@ -42,54 +43,14 @@ public static class CalendarXamlHelpers
public static string GetRecurrenceString(CalendarItemViewModel calendarItemViewModel)
{
if (calendarItemViewModel == null || !calendarItemViewModel.IsRecurringChild) return string.Empty;
// Parse recurrence rules
var calendarEvent = new CalendarEvent
{
Start = new CalDateTime(calendarItemViewModel.StartDate),
End = new CalDateTime(calendarItemViewModel.EndDate),
};
var recurrenceLines = Regex.Split(calendarItemViewModel.CalendarItem.Recurrence, Constants.CalendarEventRecurrenceRuleSeperator);
foreach (var line in recurrenceLines)
{
calendarEvent.RecurrenceRules.Add(new RecurrencePattern(line));
}
if (calendarEvent.RecurrenceRules == null || !calendarEvent.RecurrenceRules.Any())
{
return "No recurrence pattern.";
}
var recurrenceRule = calendarEvent.RecurrenceRules.First();
var daysOfWeek = string.Join(", ", recurrenceRule.ByDay.Select(day => day.DayOfWeek.ToString()));
string timeZone = calendarEvent.DtStart.TzId ?? "UTC";
return $"Every {daysOfWeek}, effective {calendarEvent.DtStart.Value.ToShortDateString()} " +
$"from {calendarEvent.DtStart.Value.ToShortTimeString()} to {calendarEvent.DtEnd.Value.ToShortTimeString()} " +
$"{timeZone}.";
// TODO
return string.Empty;
}
public static string GetDetailsPopupDurationString(CalendarItemViewModel calendarItemViewModel, CalendarSettings settings)
{
if (calendarItemViewModel == null || settings == null) return string.Empty;
// Single event in a day.
if (!calendarItemViewModel.IsAllDayEvent && !calendarItemViewModel.IsMultiDayEvent)
{
return $"{calendarItemViewModel.Period.Start.ToString("d", settings.CultureInfo)} {settings.GetTimeString(calendarItemViewModel.Period.Duration)}";
}
else if (calendarItemViewModel.IsMultiDayEvent)
{
return $"{calendarItemViewModel.Period.Start.ToString("d", settings.CultureInfo)} - {calendarItemViewModel.Period.End.ToString("d", settings.CultureInfo)}";
}
else
{
// All day event.
return $"{calendarItemViewModel.Period.Start.ToString("d", settings.CultureInfo)} ({Translator.CalendarItemAllDay})";
}
// TODO
return string.Empty;
}
public static PopupPlacementMode GetDesiredPlacementModeForEventsDetailsPopup(
@@ -98,8 +59,12 @@ public static class CalendarXamlHelpers
{
if (calendarItemViewModel == null) return PopupPlacementMode.Auto;
bool isAllDayOrMultiDay = calendarItemViewModel.CalendarItem.ItemType == CalendarItemType.MultiDay ||
calendarItemViewModel.CalendarItem.ItemType == CalendarItemType.AllDay ||
calendarItemViewModel.CalendarItem.ItemType == CalendarItemType.MultiDayAllDay;
// All and/or multi day events always go to the top of the screen.
if (calendarItemViewModel.IsAllDayEvent || calendarItemViewModel.IsMultiDayEvent) return PopupPlacementMode.Bottom;
if (isAllDayOrMultiDay) return PopupPlacementMode.Bottom;
return XamlHelpers.GetPlaccementModeForCalendarType(calendarDisplayType);
}

View File

@@ -13,7 +13,8 @@ public partial class CustomAreaCalendarItemSelector : DataTemplateSelector
{
if (item is CalendarItemViewModel calendarItemViewModel)
{
return calendarItemViewModel.IsMultiDayEvent ? MultiDayTemplate : AllDayTemplate;
return calendarItemViewModel.CalendarItem.ItemType == Core.Domain.Enums.CalendarItemType.MultiDay ||
calendarItemViewModel.CalendarItem.ItemType == Core.Domain.Enums.CalendarItemType.MultiDayAllDay ? MultiDayTemplate : AllDayTemplate;
}
return base.SelectTemplateCore(item, container);

View File

@@ -256,7 +256,7 @@
<PersonPicture
Width="40"
Height="40"
DisplayName="{x:Bind Name}" />
DisplayName="{x:Bind DisplayName}" />
<!-- TODO: Organizer -->
<Grid Grid.Column="1">
@@ -265,7 +265,7 @@
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<TextBlock FontWeight="SemiBold" Text="{x:Bind Name}" />
<TextBlock FontWeight="SemiBold" Text="{x:Bind DisplayName}" />
<TextBlock
Grid.Row="1"
FontSize="13"