From 7a0db6e72a1dcdea9a05dacd6f33ab68dffd7a9d Mon Sep 17 00:00:00 2001 From: jotalis Date: Thu, 21 Nov 2024 16:32:22 -0800 Subject: [PATCH 01/12] feat: duplicate to new schedule functionality --- apps/antalmanac/src/components/dialogs/CopySchedule.tsx | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/apps/antalmanac/src/components/dialogs/CopySchedule.tsx b/apps/antalmanac/src/components/dialogs/CopySchedule.tsx index c0722d461..c3f79c0a0 100644 --- a/apps/antalmanac/src/components/dialogs/CopySchedule.tsx +++ b/apps/antalmanac/src/components/dialogs/CopySchedule.tsx @@ -12,7 +12,7 @@ import { import { SelectChangeEvent } from '@mui/material'; import { useState, useEffect, useCallback } from 'react'; -import { copySchedule } from '$actions/AppStoreActions'; +import { copySchedule, addSchedule } from '$actions/AppStoreActions'; import AppStore from '$stores/AppStore'; interface CopyScheduleDialogProps extends DialogProps { @@ -35,6 +35,10 @@ function CopyScheduleDialog(props: CopyScheduleDialogProps) { const handleCopy = useCallback(() => { if (selectedSchedule !== scheduleNames.length) { + if (selectedSchedule === scheduleNames.length + 1) { + addSchedule('Copy of ' + scheduleNames[index]); + AppStore.changeCurrentSchedule(index); + } copySchedule(selectedSchedule); } else { scheduleNames.forEach((_, scheduleIndex) => { @@ -70,6 +74,7 @@ function CopyScheduleDialog(props: CopyScheduleDialogProps) { {name} ))} + Copy to New Schedule Copy to All Schedules From 668c3744bfda7173dddecc8bb93c246ccf401cef Mon Sep 17 00:00:00 2001 From: jotalis Date: Thu, 21 Nov 2024 16:38:33 -0800 Subject: [PATCH 02/12] feat: enforce unique schedule names when duplicating calendars --- apps/antalmanac/src/components/dialogs/CopySchedule.tsx | 2 +- apps/antalmanac/src/stores/AppStore.ts | 4 ++++ apps/antalmanac/src/stores/Schedules.ts | 5 +++++ 3 files changed, 10 insertions(+), 1 deletion(-) diff --git a/apps/antalmanac/src/components/dialogs/CopySchedule.tsx b/apps/antalmanac/src/components/dialogs/CopySchedule.tsx index c3f79c0a0..898f415d0 100644 --- a/apps/antalmanac/src/components/dialogs/CopySchedule.tsx +++ b/apps/antalmanac/src/components/dialogs/CopySchedule.tsx @@ -36,7 +36,7 @@ function CopyScheduleDialog(props: CopyScheduleDialogProps) { const handleCopy = useCallback(() => { if (selectedSchedule !== scheduleNames.length) { if (selectedSchedule === scheduleNames.length + 1) { - addSchedule('Copy of ' + scheduleNames[index]); + addSchedule(AppStore.getNextScheduleName('Copy of ' + scheduleNames[index])); AppStore.changeCurrentSchedule(index); } copySchedule(selectedSchedule); diff --git a/apps/antalmanac/src/stores/AppStore.ts b/apps/antalmanac/src/stores/AppStore.ts index bfcd43456..1851e2355 100644 --- a/apps/antalmanac/src/stores/AppStore.ts +++ b/apps/antalmanac/src/stores/AppStore.ts @@ -71,6 +71,10 @@ class AppStore extends EventEmitter { } } + getNextScheduleName(newScheduleName: string) { + return this.schedule.getNextScheduleName(newScheduleName); + } + getDefaultScheduleName() { return this.schedule.getDefaultScheduleName(); } diff --git a/apps/antalmanac/src/stores/Schedules.ts b/apps/antalmanac/src/stores/Schedules.ts index 0129082ff..5dfb7d530 100644 --- a/apps/antalmanac/src/stores/Schedules.ts +++ b/apps/antalmanac/src/stores/Schedules.ts @@ -50,6 +50,11 @@ export class Schedules { this.skeletonSchedules = []; } + getNextScheduleName(newScheduleName: string) { + const countSameScheduleNames = this.getScheduleNames().filter((name) => name.includes(newScheduleName)).length; + return `${newScheduleName + (countSameScheduleNames == 0 ? '' : '(' + countSameScheduleNames + ')')}`; + } + getDefaultScheduleName() { const termName = termData[0].shortName.replaceAll(' ', '-'); const countSameScheduleNames = this.getScheduleNames().filter((name) => name.includes(termName)).length; From 2709024377d3390408792f9b71d0137f8489609b Mon Sep 17 00:00:00 2001 From: jotalis Date: Thu, 21 Nov 2024 19:41:08 -0800 Subject: [PATCH 03/12] fix: add explicit check to calc duplicate count --- apps/antalmanac/src/stores/Schedules.ts | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/apps/antalmanac/src/stores/Schedules.ts b/apps/antalmanac/src/stores/Schedules.ts index 5dfb7d530..4d7e28f08 100644 --- a/apps/antalmanac/src/stores/Schedules.ts +++ b/apps/antalmanac/src/stores/Schedules.ts @@ -51,8 +51,15 @@ export class Schedules { } getNextScheduleName(newScheduleName: string) { - const countSameScheduleNames = this.getScheduleNames().filter((name) => name.includes(newScheduleName)).length; - return `${newScheduleName + (countSameScheduleNames == 0 ? '' : '(' + countSameScheduleNames + ')')}`; + const scheduleNames = this.getScheduleNames(); + let nextScheduleName = newScheduleName; + let counter = 1; + + while (scheduleNames.includes(nextScheduleName)) { + nextScheduleName = `${newScheduleName}(${counter++})`; + } + + return nextScheduleName; } getDefaultScheduleName() { From 151be5fe6b0c3a51811cf78bc71e6adfd6cbfb7d Mon Sep 17 00:00:00 2001 From: jotalis Date: Sat, 23 Nov 2024 19:38:46 -0800 Subject: [PATCH 04/12] feat: remove other copy schedule functionality except make a copy --- .../src/components/dialogs/CopySchedule.tsx | 59 ++++--------------- 1 file changed, 13 insertions(+), 46 deletions(-) diff --git a/apps/antalmanac/src/components/dialogs/CopySchedule.tsx b/apps/antalmanac/src/components/dialogs/CopySchedule.tsx index 898f415d0..694eb4ece 100644 --- a/apps/antalmanac/src/components/dialogs/CopySchedule.tsx +++ b/apps/antalmanac/src/components/dialogs/CopySchedule.tsx @@ -5,12 +5,10 @@ import { DialogActions, DialogContent, DialogTitle, - MenuItem, - Select, + TextField, type DialogProps, } from '@mui/material'; -import { SelectChangeEvent } from '@mui/material'; -import { useState, useEffect, useCallback } from 'react'; +import { useState, useCallback } from 'react'; import { copySchedule, addSchedule } from '$actions/AppStoreActions'; import AppStore from '$stores/AppStore'; @@ -22,11 +20,11 @@ interface CopyScheduleDialogProps extends DialogProps { function CopyScheduleDialog(props: CopyScheduleDialogProps) { const { index } = props; const { onClose } = props; // destructured separately for memoization. - const [scheduleNames, setScheduleNames] = useState(AppStore.getScheduleNames()); - const [selectedSchedule, setSelectedSchedule] = useState(0); + const scheduleNames = AppStore.getScheduleNames(); + const [name, setName] = useState(`Copy of ${scheduleNames[index]}`); - const handleScheduleChange = useCallback((event: SelectChangeEvent) => { - setSelectedSchedule(event.target.value as number); + const handleNameChange = useCallback((event: React.ChangeEvent) => { + setName(event.target.value); }, []); const handleCancel = useCallback(() => { @@ -34,49 +32,18 @@ function CopyScheduleDialog(props: CopyScheduleDialogProps) { }, [onClose]); const handleCopy = useCallback(() => { - if (selectedSchedule !== scheduleNames.length) { - if (selectedSchedule === scheduleNames.length + 1) { - addSchedule(AppStore.getNextScheduleName('Copy of ' + scheduleNames[index])); - AppStore.changeCurrentSchedule(index); - } - copySchedule(selectedSchedule); - } else { - scheduleNames.forEach((_, scheduleIndex) => { - if (scheduleIndex !== index) { - copySchedule(scheduleIndex); - } - }); - } + addSchedule(AppStore.getNextScheduleName(name)); + AppStore.changeCurrentSchedule(index); + copySchedule(AppStore.getScheduleNames().length - 1); onClose?.({}, 'escapeKeyDown'); - }, [index, onClose, selectedSchedule, scheduleNames]); - - const handleScheduleNamesChange = useCallback(() => { - setScheduleNames([...AppStore.getScheduleNames()]); - }, []); - - useEffect(() => { - AppStore.on('scheduleNamesChange', handleScheduleNamesChange); - - return () => { - AppStore.off('scheduleNamesChange', handleScheduleNamesChange); - }; - }, [handleScheduleNamesChange]); + }, [index, onClose]); return ( - Copy To Schedule - + Copy Schedule - + @@ -85,7 +52,7 @@ function CopyScheduleDialog(props: CopyScheduleDialogProps) { Cancel From 624102f9eb5b135f3f0e974985b8aba0defaefd0 Mon Sep 17 00:00:00 2001 From: jotalis Date: Sat, 23 Nov 2024 22:35:18 -0800 Subject: [PATCH 05/12] refactor: abstract duplicate schedule functionality and deprecate copy to schedule --- .../src/actions/ActionTypesStore.ts | 4 +-- .../antalmanac/src/actions/AppStoreActions.ts | 12 ++++----- .../src/components/dialogs/CopySchedule.tsx | 27 ++++++++++++------- apps/antalmanac/src/stores/AppStore.ts | 9 ++++--- apps/antalmanac/src/stores/Schedules.ts | 21 ++++++++++++++- 5 files changed, 51 insertions(+), 22 deletions(-) diff --git a/apps/antalmanac/src/actions/ActionTypesStore.ts b/apps/antalmanac/src/actions/ActionTypesStore.ts index c57d018a3..0284234ef 100644 --- a/apps/antalmanac/src/actions/ActionTypesStore.ts +++ b/apps/antalmanac/src/actions/ActionTypesStore.ts @@ -59,7 +59,7 @@ export interface ClearScheduleAction { export interface CopyScheduleAction { type: 'copySchedule'; - to: number; + newScheduleName: string; } export interface ChangeCourseColorAction { @@ -159,7 +159,7 @@ class ActionTypesStore extends EventEmitter { AppStore.schedule.clearCurrentSchedule(); break; case 'copySchedule': - AppStore.schedule.copySchedule(action.to); + AppStore.schedule.copySchedule(action.newScheduleName); break; default: break; diff --git a/apps/antalmanac/src/actions/AppStoreActions.ts b/apps/antalmanac/src/actions/AppStoreActions.ts index 78bbf2c55..e54a5be49 100644 --- a/apps/antalmanac/src/actions/AppStoreActions.ts +++ b/apps/antalmanac/src/actions/AppStoreActions.ts @@ -11,8 +11,8 @@ import { removeLocalStorageUserId, setLocalStorageUserId } from '$lib/localStora import AppStore from '$stores/AppStore'; export interface CopyScheduleOptions { - onSuccess: (index: number) => unknown; - onError: (index: number) => unknown; + onSuccess: (scheduleName: string) => unknown; + onError: (scheduleName: string) => unknown; } export const addCourse = ( @@ -250,17 +250,17 @@ export const changeCourseColor = (sectionCode: string, term: string, newColor: s AppStore.changeCourseColor(sectionCode, term, newColor); }; -export const copySchedule = (to: number, options?: CopyScheduleOptions) => { +export const copySchedule = (newScheduleName: string, options?: CopyScheduleOptions) => { logAnalytics({ category: analyticsEnum.addedClasses.title, action: analyticsEnum.addedClasses.actions.COPY_SCHEDULE, }); try { - AppStore.copySchedule(to); - options?.onSuccess(to); + AppStore.copySchedule(newScheduleName); + options?.onSuccess(newScheduleName); } catch (error) { - options?.onError(to); + options?.onError(newScheduleName); } }; diff --git a/apps/antalmanac/src/components/dialogs/CopySchedule.tsx b/apps/antalmanac/src/components/dialogs/CopySchedule.tsx index 694eb4ece..5b5a967c4 100644 --- a/apps/antalmanac/src/components/dialogs/CopySchedule.tsx +++ b/apps/antalmanac/src/components/dialogs/CopySchedule.tsx @@ -8,9 +8,9 @@ import { TextField, type DialogProps, } from '@mui/material'; -import { useState, useCallback } from 'react'; +import { useState, useEffect, useCallback } from 'react'; -import { copySchedule, addSchedule } from '$actions/AppStoreActions'; +import { copySchedule } from '$actions/AppStoreActions'; import AppStore from '$stores/AppStore'; interface CopyScheduleDialogProps extends DialogProps { @@ -20,8 +20,7 @@ interface CopyScheduleDialogProps extends DialogProps { function CopyScheduleDialog(props: CopyScheduleDialogProps) { const { index } = props; const { onClose } = props; // destructured separately for memoization. - const scheduleNames = AppStore.getScheduleNames(); - const [name, setName] = useState(`Copy of ${scheduleNames[index]}`); + const [name, setName] = useState(`Copy of ${AppStore.getScheduleNames()[index]}`); const handleNameChange = useCallback((event: React.ChangeEvent) => { setName(event.target.value); @@ -32,21 +31,29 @@ function CopyScheduleDialog(props: CopyScheduleDialogProps) { }, [onClose]); const handleCopy = useCallback(() => { - addSchedule(AppStore.getNextScheduleName(name)); - AppStore.changeCurrentSchedule(index); - copySchedule(AppStore.getScheduleNames().length - 1); + copySchedule(name); onClose?.({}, 'escapeKeyDown'); - }, [index, onClose]); + }, [onClose, name]); + + const handleScheduleNamesChange = useCallback(() => { + setName(`Copy of ${AppStore.getScheduleNames()[index]}`); + }, [index]); + + useEffect(() => { + AppStore.on('scheduleNamesChange', handleScheduleNamesChange); + return () => { + AppStore.off('scheduleNamesChange', handleScheduleNamesChange); + }; + }, [handleScheduleNamesChange]); return ( Copy Schedule - + - - From 864c1ad63ecaa1529226c8e6ad3e761c82891193 Mon Sep 17 00:00:00 2001 From: jotalis Date: Sat, 23 Nov 2024 22:40:20 -0800 Subject: [PATCH 07/12] chore: restore text field label --- apps/antalmanac/src/components/dialogs/CopySchedule.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/antalmanac/src/components/dialogs/CopySchedule.tsx b/apps/antalmanac/src/components/dialogs/CopySchedule.tsx index c5412c735..d6d657a33 100644 --- a/apps/antalmanac/src/components/dialogs/CopySchedule.tsx +++ b/apps/antalmanac/src/components/dialogs/CopySchedule.tsx @@ -51,7 +51,7 @@ function CopyScheduleDialog(props: CopyScheduleDialogProps) { Copy Schedule - + From 6eb0ef07322f25f635d16cb4a2eb32ea4337207f Mon Sep 17 00:00:00 2001 From: jotalis Date: Sun, 24 Nov 2024 01:39:01 -0800 Subject: [PATCH 08/12] feat: enforce unique naming validation across renaming and creating new schedules --- .../src/components/dialogs/AddSchedule.tsx | 18 +++++++++++++++--- .../src/components/dialogs/RenameSchedule.tsx | 12 ++++-------- apps/antalmanac/src/stores/AppStore.ts | 4 ++-- apps/antalmanac/src/stores/Schedules.ts | 18 ++++++++---------- 4 files changed, 29 insertions(+), 23 deletions(-) diff --git a/apps/antalmanac/src/components/dialogs/AddSchedule.tsx b/apps/antalmanac/src/components/dialogs/AddSchedule.tsx index 3bf91f87a..e458d973c 100644 --- a/apps/antalmanac/src/components/dialogs/AddSchedule.tsx +++ b/apps/antalmanac/src/components/dialogs/AddSchedule.tsx @@ -1,6 +1,6 @@ import { Box, Button, Dialog, DialogActions, DialogContent, DialogTitle, TextField } from '@mui/material'; import type { DialogProps } from '@mui/material'; -import { useState } from 'react'; +import { useState, useEffect, useCallback } from 'react'; import { addSchedule } from '$actions/AppStoreActions'; import AppStore from '$stores/AppStore'; @@ -12,7 +12,9 @@ import { useThemeStore } from '$stores/SettingsStore'; function AddScheduleDialog({ onClose, onKeyDown, ...props }: DialogProps) { const isDark = useThemeStore((store) => store.isDark); - const [name, setName] = useState(AppStore.getDefaultScheduleName()); + const [name, setName] = useState( + AppStore.getNextScheduleName(AppStore.getDefaultScheduleName(), AppStore.getScheduleNames().length) + ); const handleCancel = () => { onClose?.({}, 'escapeKeyDown'); @@ -24,7 +26,6 @@ function AddScheduleDialog({ onClose, onKeyDown, ...props }: DialogProps) { const submitName = () => { addSchedule(name); - setName(AppStore.schedule.getDefaultScheduleName()); onClose?.({}, 'escapeKeyDown'); }; @@ -46,6 +47,17 @@ function AddScheduleDialog({ onClose, onKeyDown, ...props }: DialogProps) { } }; + const handleScheduleNamesChange = useCallback(() => { + setName(AppStore.getNextScheduleName(AppStore.getDefaultScheduleName(), AppStore.getScheduleNames().length)); + }, []); + + useEffect(() => { + AppStore.on('scheduleNamesChange', handleScheduleNamesChange); + return () => { + AppStore.off('scheduleNamesChange', handleScheduleNamesChange); + }; + }, [handleScheduleNamesChange]); + return ( Add Schedule diff --git a/apps/antalmanac/src/components/dialogs/RenameSchedule.tsx b/apps/antalmanac/src/components/dialogs/RenameSchedule.tsx index 0d3611a2a..718f8cab8 100644 --- a/apps/antalmanac/src/components/dialogs/RenameSchedule.tsx +++ b/apps/antalmanac/src/components/dialogs/RenameSchedule.tsx @@ -34,10 +34,7 @@ function RenameScheduleDialog(props: ScheduleNameDialogProps) { * This is destructured separately for memoization. */ const { onClose } = props; - - const [scheduleNames, setScheduleNames] = useState(AppStore.getScheduleNames()); - - const [name, setName] = useState(scheduleNames[index]); + const [name, setName] = useState(AppStore.getScheduleNames()[index]); const disabled = useMemo(() => { return name?.trim() === ''; @@ -45,8 +42,7 @@ function RenameScheduleDialog(props: ScheduleNameDialogProps) { const handleCancel = useCallback(() => { onClose?.({}, 'escapeKeyDown'); - setName(scheduleNames[index]); - }, [onClose, scheduleNames, index]); + }, [onClose, index]); const handleNameChange = useCallback((event: React.ChangeEvent) => { setName(event.target.value); @@ -75,8 +71,8 @@ function RenameScheduleDialog(props: ScheduleNameDialogProps) { ); const handleScheduleNamesChange = useCallback(() => { - setScheduleNames(AppStore.getScheduleNames()); - }, []); + setName(AppStore.getScheduleNames()[index]); + }, [index]); useEffect(() => { AppStore.on('scheduleNamesChange', handleScheduleNamesChange); diff --git a/apps/antalmanac/src/stores/AppStore.ts b/apps/antalmanac/src/stores/AppStore.ts index abec5e2f0..b9ac5c496 100644 --- a/apps/antalmanac/src/stores/AppStore.ts +++ b/apps/antalmanac/src/stores/AppStore.ts @@ -71,8 +71,8 @@ class AppStore extends EventEmitter { } } - getNextScheduleName(newScheduleName: string) { - return this.schedule.getNextScheduleName(newScheduleName); + getNextScheduleName(newScheduleName: string, scheduleIndex: number) { + return this.schedule.getNextScheduleName(newScheduleName, scheduleIndex); } getDefaultScheduleName() { diff --git a/apps/antalmanac/src/stores/Schedules.ts b/apps/antalmanac/src/stores/Schedules.ts index 02926b16c..84c68612a 100644 --- a/apps/antalmanac/src/stores/Schedules.ts +++ b/apps/antalmanac/src/stores/Schedules.ts @@ -50,22 +50,19 @@ export class Schedules { this.skeletonSchedules = []; } - getNextScheduleName(newScheduleName: string) { - const scheduleNames = this.getScheduleNames(); + getNextScheduleName(newScheduleName: string, scheduleIndex: number) { + const scheduleNames = this.getScheduleNames().filter((_, index) => index !== scheduleIndex); let nextScheduleName = newScheduleName; let counter = 1; while (scheduleNames.includes(nextScheduleName)) { nextScheduleName = `${newScheduleName}(${counter++})`; } - return nextScheduleName; } getDefaultScheduleName() { - const termName = termData[0].shortName.replaceAll(' ', '-'); - const countSameScheduleNames = this.getScheduleNames().filter((name) => name.includes(termName)).length; - return `${termName + (countSameScheduleNames == 0 ? '' : '(' + countSameScheduleNames + ')')}`; + return termData[0].shortName.replaceAll(' ', '-'); } getCurrentScheduleIndex() { @@ -104,12 +101,13 @@ export class Schedules { /** * Create an empty schedule. + * @param newScheduleName The name of the new schedule. If a schedule with the same name already exists, a number will be appended to the name. */ addNewSchedule(newScheduleName: string) { this.addUndoState(); const scheduleNoteId = Math.random(); this.schedules.push({ - scheduleName: newScheduleName, + scheduleName: this.getNextScheduleName(newScheduleName, this.getNumberOfSchedules()), courses: [], customEvents: [], scheduleNoteId: scheduleNoteId, @@ -121,10 +119,11 @@ export class Schedules { /** * Rename schedule with the specified index. + * @param newScheduleName The name of the new schedule. If a schedule with the same name already exists, a number will be appended to the name. */ renameSchedule(newScheduleName: string, scheduleIndex: number) { this.addUndoState(); - this.schedules[scheduleIndex].scheduleName = newScheduleName; + this.schedules[scheduleIndex].scheduleName = this.getNextScheduleName(newScheduleName, scheduleIndex); } /** @@ -171,10 +170,9 @@ export class Schedules { /** * Copy the current schedule to a newly created schedule with the specified name. - * @param newScheduleName The name of the new schedule. If a schedule with the same name already exists, a number will be appended to the name. */ copySchedule(newScheduleName: string) { - this.addNewSchedule(this.getNextScheduleName(newScheduleName)); + this.addNewSchedule(newScheduleName); this.currentScheduleIndex = this.previousStates[this.previousStates.length - 1].scheduleIndex; // return to previous schedule index for copying const to = this.getNumberOfSchedules() - 1; From e4fd838659d92fd461e23953ca7cefacfa6a0259 Mon Sep 17 00:00:00 2001 From: jotalis Date: Sun, 24 Nov 2024 01:46:11 -0800 Subject: [PATCH 09/12] chore: remove dep --- apps/antalmanac/src/components/dialogs/RenameSchedule.tsx | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) diff --git a/apps/antalmanac/src/components/dialogs/RenameSchedule.tsx b/apps/antalmanac/src/components/dialogs/RenameSchedule.tsx index 718f8cab8..472bf9fd6 100644 --- a/apps/antalmanac/src/components/dialogs/RenameSchedule.tsx +++ b/apps/antalmanac/src/components/dialogs/RenameSchedule.tsx @@ -8,7 +8,7 @@ import { TextField, type DialogProps, } from '@mui/material'; -import { useCallback, useState, useEffect, useMemo } from 'react'; +import { useCallback, useState, useEffect } from 'react'; import { renameSchedule } from '$actions/AppStoreActions'; import AppStore from '$stores/AppStore'; @@ -36,10 +36,6 @@ function RenameScheduleDialog(props: ScheduleNameDialogProps) { const { onClose } = props; const [name, setName] = useState(AppStore.getScheduleNames()[index]); - const disabled = useMemo(() => { - return name?.trim() === ''; - }, [name]); - const handleCancel = useCallback(() => { onClose?.({}, 'escapeKeyDown'); }, [onClose, index]); @@ -96,7 +92,7 @@ function RenameScheduleDialog(props: ScheduleNameDialogProps) { - From f7979bc5ca418fd4825233252cffa80cc305cf4c Mon Sep 17 00:00:00 2001 From: jotalis Date: Sun, 24 Nov 2024 02:00:19 -0800 Subject: [PATCH 10/12] chore: code safety on schedule name --- apps/antalmanac/src/components/dialogs/AddSchedule.tsx | 2 +- apps/antalmanac/src/components/dialogs/CopySchedule.tsx | 2 +- apps/antalmanac/src/components/dialogs/RenameSchedule.tsx | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/apps/antalmanac/src/components/dialogs/AddSchedule.tsx b/apps/antalmanac/src/components/dialogs/AddSchedule.tsx index e458d973c..ae4bc6305 100644 --- a/apps/antalmanac/src/components/dialogs/AddSchedule.tsx +++ b/apps/antalmanac/src/components/dialogs/AddSchedule.tsx @@ -72,7 +72,7 @@ function AddScheduleDialog({ onClose, onKeyDown, ...props }: DialogProps) { - diff --git a/apps/antalmanac/src/components/dialogs/CopySchedule.tsx b/apps/antalmanac/src/components/dialogs/CopySchedule.tsx index d6d657a33..5a9da35d5 100644 --- a/apps/antalmanac/src/components/dialogs/CopySchedule.tsx +++ b/apps/antalmanac/src/components/dialogs/CopySchedule.tsx @@ -58,7 +58,7 @@ function CopyScheduleDialog(props: CopyScheduleDialogProps) { - diff --git a/apps/antalmanac/src/components/dialogs/RenameSchedule.tsx b/apps/antalmanac/src/components/dialogs/RenameSchedule.tsx index 472bf9fd6..a365413d3 100644 --- a/apps/antalmanac/src/components/dialogs/RenameSchedule.tsx +++ b/apps/antalmanac/src/components/dialogs/RenameSchedule.tsx @@ -92,7 +92,7 @@ function RenameScheduleDialog(props: ScheduleNameDialogProps) { - From eac877d963bc85fd79dd3602b4d1e35f43a93946 Mon Sep 17 00:00:00 2001 From: jotalis Date: Sun, 24 Nov 2024 22:16:56 -0800 Subject: [PATCH 11/12] fix: delete schedule modal displays correct schedule name on consecutive deletes --- .../src/components/dialogs/DeleteSchedule.tsx | 21 +++++++++++++------ 1 file changed, 15 insertions(+), 6 deletions(-) diff --git a/apps/antalmanac/src/components/dialogs/DeleteSchedule.tsx b/apps/antalmanac/src/components/dialogs/DeleteSchedule.tsx index 2bcf7ed96..402bf1d40 100644 --- a/apps/antalmanac/src/components/dialogs/DeleteSchedule.tsx +++ b/apps/antalmanac/src/components/dialogs/DeleteSchedule.tsx @@ -7,7 +7,7 @@ import { DialogTitle, type DialogProps, } from '@mui/material'; -import { useCallback, useMemo } from 'react'; +import { useCallback, useEffect, useState } from 'react'; import { deleteSchedule } from '$actions/AppStoreActions'; import AppStore from '$stores/AppStore'; @@ -35,10 +35,7 @@ function DeleteScheduleDialog(props: ScheduleNameDialogProps) { * This is destructured separately for memoization. */ const { onClose } = props; - - const scheduleName = useMemo(() => { - return AppStore.schedule.getScheduleName(index); - }, [index]); + const [name, setName] = useState(AppStore.getScheduleNames()[index]); const handleCancel = useCallback(() => { onClose?.({}, 'escapeKeyDown'); @@ -49,12 +46,24 @@ function DeleteScheduleDialog(props: ScheduleNameDialogProps) { onClose?.({}, 'escapeKeyDown'); }, [index, onClose]); + const handleScheduleNamesChange = useCallback(() => { + setName(AppStore.getScheduleNames()[index]); + }, [index]); + + useEffect(() => { + AppStore.on('scheduleNamesChange', handleScheduleNamesChange); + + return () => { + AppStore.off('scheduleNamesChange', handleScheduleNamesChange); + }; + }, [handleScheduleNamesChange]); + return ( Delete Schedule - Are you sure you want to delete "{scheduleName}"? + Are you sure you want to delete "{name}"? From 31a86eacc95e208a3a4f1425e6fdd2a5b447f4ae Mon Sep 17 00:00:00 2001 From: jotalis Date: Mon, 25 Nov 2024 23:48:29 -0800 Subject: [PATCH 12/12] chore: delete unused code and use filter using splice --- apps/antalmanac/src/stores/Schedules.ts | 27 ++----------------------- 1 file changed, 2 insertions(+), 25 deletions(-) diff --git a/apps/antalmanac/src/stores/Schedules.ts b/apps/antalmanac/src/stores/Schedules.ts index 84c68612a..9d14a983e 100644 --- a/apps/antalmanac/src/stores/Schedules.ts +++ b/apps/antalmanac/src/stores/Schedules.ts @@ -51,7 +51,8 @@ export class Schedules { } getNextScheduleName(newScheduleName: string, scheduleIndex: number) { - const scheduleNames = this.getScheduleNames().filter((_, index) => index !== scheduleIndex); + const scheduleNames = this.getScheduleNames(); + scheduleNames.splice(scheduleIndex, 1); let nextScheduleName = newScheduleName; let counter = 1; @@ -144,30 +145,6 @@ export class Schedules { this.currentScheduleIndex = Math.min(scheduleIndex, this.getNumberOfSchedules() - 1); } - /** - * @deprecated This method is no longer used by any features - * Append all courses from current schedule to the schedule with the target index. - * @param to Index of the schedule to append courses to. If equal to number of schedules, will append courses to all schedules. - */ - copyToSchedule(to: number) { - this.addUndoState(); - for (const course of this.getCurrentCourses()) { - if (to === this.getNumberOfSchedules()) { - this.addCourseToAllSchedules(course); - } else { - this.addCourse(course, to, false); - } - } - - for (const customEvent of this.getCurrentCustomEvents()) { - if (to === this.getNumberOfSchedules()) { - this.addCustomEvent(customEvent, [...Array(to).keys()]); - } else { - this.addCustomEvent(customEvent, [to]); - } - } - } - /** * Copy the current schedule to a newly created schedule with the specified name. */