diff --git a/frontend/app/components/workspace/CrmWorkspaceApp.vue b/frontend/app/components/workspace/CrmWorkspaceApp.vue index 667454b..a9349cd 100644 --- a/frontend/app/components/workspace/CrmWorkspaceApp.vue +++ b/frontend/app/components/workspace/CrmWorkspaceApp.vue @@ -2310,6 +2310,10 @@ onBeforeUnmount(() => { clearInterval(lifecycleClock); lifecycleClock = null; } + if (calendarViewportResizeObserver) { + calendarViewportResizeObserver.disconnect(); + calendarViewportResizeObserver = null; + } clearCalendarZoomPrime(); }); @@ -2360,16 +2364,29 @@ type CalendarRect = { left: number; top: number; width: number; height: number } const calendarContentWrapRef = ref(null); const calendarContentScrollRef = ref(null); const calendarSceneRef = ref(null); +const calendarViewportHeight = ref(0); const calendarHoveredMonthIndex = ref(null); const calendarHoveredWeekStartKey = ref(""); const calendarHoveredDayKey = ref(""); +let calendarViewportResizeObserver: ResizeObserver | null = null; function setCalendarContentWrapRef(element: HTMLElement | null) { calendarContentWrapRef.value = element; } function setCalendarContentScrollRef(element: HTMLElement | null) { + if (calendarViewportResizeObserver) { + calendarViewportResizeObserver.disconnect(); + calendarViewportResizeObserver = null; + } calendarContentScrollRef.value = element; + if (element && typeof ResizeObserver !== "undefined") { + calendarViewportResizeObserver = new ResizeObserver(() => { + calendarViewportHeight.value = Math.max(0, Math.round(element.clientHeight)); + }); + calendarViewportResizeObserver.observe(element); + calendarViewportHeight.value = Math.max(0, Math.round(element.clientHeight)); + } } function setCalendarSceneRef(element: HTMLElement | null) { @@ -4765,6 +4782,7 @@ async function decideFeedCard(card: FeedCard, decision: "accepted" | "rejected") :set-calendar-content-scroll-ref="setCalendarContentScrollRef" :on-calendar-hierarchy-wheel="onCalendarHierarchyWheel" :set-calendar-scene-ref="setCalendarSceneRef" + :calendar-viewport-height="calendarViewportHeight" :normalized-calendar-view="normalizedCalendarView" :calendar-scene-transform-style="calendarSceneTransformStyle" :on-calendar-scene-mouse-leave="onCalendarSceneMouseLeave" diff --git a/frontend/app/components/workspace/calendar/CrmCalendarPanel.vue b/frontend/app/components/workspace/calendar/CrmCalendarPanel.vue index f88bcb2..6c45e6c 100644 --- a/frontend/app/components/workspace/calendar/CrmCalendarPanel.vue +++ b/frontend/app/components/workspace/calendar/CrmCalendarPanel.vue @@ -52,6 +52,7 @@ defineProps<{ setCalendarContentScrollRef: (element: HTMLDivElement | null) => void; onCalendarHierarchyWheel: (event: WheelEvent) => void; setCalendarSceneRef: (element: HTMLDivElement | null) => void; + calendarViewportHeight: number; normalizedCalendarView: string; calendarSceneTransformStyle: Record; onCalendarSceneMouseLeave: () => void; @@ -182,7 +183,12 @@ defineProps<{ calendarHoveredMonthIndex === item.monthIndex ? 'calendar-hover-target' : '', calendarZoomPrimeToken === calendarPrimeMonthToken(item.monthIndex) ? 'calendar-zoom-prime-active' : '', ]" - :style="calendarPrimeStyle(calendarPrimeMonthToken(item.monthIndex))" + :style="{ + ...calendarPrimeStyle(calendarPrimeMonthToken(item.monthIndex)), + ...(calendarView !== 'year' && item.monthIndex === calendarCursorMonth && calendarViewportHeight > 0 + ? { minHeight: `${Math.max(420, calendarViewportHeight)}px` } + : {}), + }" :data-calendar-month-index="item.monthIndex" @mouseenter="setCalendarHoveredMonthIndex(item.monthIndex)" @click="calendarView === 'year' ? zoomToMonth(item.monthIndex) : undefined"