diff --git a/components/ScheduleEditor.vue b/components/ScheduleEditor.vue new file mode 100644 index 0000000..cf4b690 --- /dev/null +++ b/components/ScheduleEditor.vue @@ -0,0 +1,291 @@ + + + + + + diff --git a/pages/index/index.vue b/pages/index/index.vue index 03aaef4..06bcd82 100644 --- a/pages/index/index.vue +++ b/pages/index/index.vue @@ -7,39 +7,12 @@ - - - - - - - - - - - - - - - - - - - - - + @@ -75,10 +48,9 @@ import { ref, computed, watch, onMounted } from 'vue'; import { onShow } from '@dcloudio/uni-app'; -import TimeTable from '@/components/TimeTable.vue'; import FabPlus from '@/components/FabPlus.vue'; import AddEventModal from '@/components/AddEventModal.vue'; -import MonthCalendar from '@/components/MonthCalendar.vue'; +import ScheduleEditor from '@/components/ScheduleEditor.vue'; import ContentDashboard from '@/components/ContentDashboard.vue'; import TodoList from '@/components/TodoList.vue'; import MessageContent from '@/components/MessageContent.vue'; @@ -98,11 +70,9 @@ function clickTab(item) { console.log('切换tab:', item.name); } -// 当前选择的日期,格式:YYYY-MM-DD +// 当前选择的日期,格式:YYYY-MM-DD(用于新建日程时传递日期) const selectedDate = ref(new Date().toISOString().slice(0, 10)); -// 小时段 -const hours = Array.from({length: 24}, (_,i)=>i); // 0~23点 // 示例日程 const today = new Date().toISOString().slice(0, 10); // 获取明天的日期 @@ -121,59 +91,28 @@ const allEvents = ref([ {id:6,title:'昨天的日程3',startHour:10,startMin:30,color:'#e3fae6',date:yesterdayStr}, ]); -// 根据当前选择日期过滤 -const eventsInDay = computed(() => { - const filtered = allEvents.value.filter(e=>e.date===selectedDate.value); - console.log('计算 eventsInDay,selectedDate:', selectedDate.value, '过滤后事件数:', filtered.length); - return filtered; -}); - -// 计算相邻日期 -const prevDate = computed(() => { - const date = new Date(selectedDate.value); - date.setDate(date.getDate() - 1); - return date.toISOString().slice(0, 10); -}); - -const nextDate = computed(() => { - const date = new Date(selectedDate.value); - date.setDate(date.getDate() + 1); - return date.toISOString().slice(0, 10); -}); - -// 前一天的事件 -const prevDayEvents = computed(() => { - return allEvents.value.filter(e => e.date === prevDate.value); -}); - -// 后一天的事件 -const nextDayEvents = computed(() => { - return allEvents.value.filter(e => e.date === nextDate.value); -}); - -// 监控 selectedDate 的变化 -watch(selectedDate, (newDate, oldDate) => { - console.log('selectedDate 发生变化:', oldDate, '->', newDate); - console.log('eventsInDay 新值:', eventsInDay.value); -}, { immediate: true }); - -// 处理日期变化 +// 处理日期变化(从 ScheduleEditor 组件传来) const handleDateChange = (dateStr) => { selectedDate.value = dateStr; console.log('通过日历组件更新选择日期:', selectedDate.value); - console.log('过滤后的事件数:', eventsInDay.value.length); } // 悬浮按钮/弹窗控制 const showAdd = ref(false); +// ScheduleEditor 组件引用 +const scheduleEditorRef = ref(null); + // 处理添加按钮点击 const handleAddClick = () => { + // 从 ScheduleEditor 组件获取当前选择的日期 + const currentDate = scheduleEditorRef.value?.selectedDate || selectedDate.value; uni.navigateTo({ - url: `/pages/add-event/index?date=${selectedDate.value}` + url: `/pages/add-event/index?date=${currentDate}` }); }; + // 添加日程 function addEvent(e) { // e是{title, startHour, startMin, color, date等},如果没有date则使用selectedDate @@ -187,171 +126,6 @@ function addEvent(e) { const value=ref(0); -// 滑动相关变量 -const touchStartX = ref(0); -const touchStartY = ref(0); -const screenWidth = ref(375); // 屏幕宽度,默认值,会在mounted时更新 -const translateX = ref(-375); // 当前滑动偏移量,初始值设为 -375(假设屏幕宽度,会在mounted时更新) -const baseTranslateX = ref(-375); // 基础偏移量 -const isAnimating = ref(false); // 是否正在执行动画 -const isDragging = ref(false); // 是否正在拖动 -const isInitialized = ref(false); // 是否已完成初始化 - -// 初始化屏幕宽度 -const initScreenWidth = () => { - uni.getSystemInfo({ - success: (res) => { - const width = res.windowWidth || res.screenWidth || 375; - screenWidth.value = width; - // 只有在未初始化时才更新,避免覆盖用户操作 - if (!isInitialized.value) { - translateX.value = -width; - baseTranslateX.value = -width; - isInitialized.value = true; - } - } - }); -}; - -// 触摸开始 -const handleTouchStart = (e) => { - if (isAnimating.value) return; - const touch = e.touches[0]; - touchStartX.value = touch.clientX; - touchStartY.value = touch.clientY; - isDragging.value = true; - baseTranslateX.value = translateX.value; // 保存当前偏移量 -}; - -// 触摸移动 -const handleTouchMove = (e) => { - if (!isDragging.value || isAnimating.value) return; - - const touch = e.touches[0]; - const deltaX = touch.clientX - touchStartX.value; - const deltaY = Math.abs(touch.clientY - touchStartY.value); - - // // 如果是水平滑动(水平距离大于垂直距离),阻止页面滚动 - // if (Math.abs(deltaX) > deltaY && Math.abs(deltaX) > 10) { - // e.preventDefault(); - // } - - // 实时更新偏移量 - translateX.value = baseTranslateX.value + deltaX; - - // 限制滑动范围(不能超出左右边界) - const minTranslate = -screenWidth.value * 2; // 最左边(昨天) - const maxTranslate = 0; // 最右边(明天) - translateX.value = Math.max(minTranslate, Math.min(maxTranslate, translateX.value)); -}; - -// 触摸结束 -const handleTouchEnd = (e) => { - if (!isDragging.value || isAnimating.value) return; - - const touch = e.changedTouches[0]; - const deltaX = touch.clientX - touchStartX.value; - const deltaY = Math.abs(touch.clientY - touchStartY.value); - const minSwipeDistance = screenWidth.value * 0.2; // 最小滑动距离为屏幕宽度的20% - - // 判断是否为有效的水平滑动 - const isHorizontalSwipe = Math.abs(deltaX) > deltaY && Math.abs(deltaX) > minSwipeDistance; - - isDragging.value = false; - - if (isHorizontalSwipe) { - // 滑动距离超过阈值,自动滑动到下一个页面 - if (deltaX > 0) { - // 向左滑动,滑动到前一天的位置 - slideToPreviousDay(); - } else { - // 向右滑动,滑动到后一天的位置 - slideToNextDay(); - } - } else { - // 滑动距离不够,回到中间位置 - resetToCenter(); - } -}; - -// 重置到中心位置(今天) -const resetToCenter = () => { - isAnimating.value = true; - translateX.value = -screenWidth.value; - - setTimeout(() => { - isAnimating.value = false; - }, 0); // 与 transition 时间一致(0.3s) -}; - -// 滑动到前一天的位置(动画完成后更新日期) -const slideToPreviousDay = () => { - isAnimating.value = true; - // 从当前位置继续滑动到前一天的完整位置(-screenWidth * 2) - const targetX = -screenWidth.value; - translateX.value = targetX; - - // 等待动画完成(300ms,与 transition 时间一致) - setTimeout(() => { - // 滑动动画完成后,先暂时禁用 transition - isAnimating.value = false; - - // 在下一帧更新日期和重置位置(确保没有 transition 动画) - setTimeout(() => { - // 更新日期 - const currentDate = new Date(selectedDate.value); - currentDate.setDate(currentDate.getDate() - 1); - selectedDate.value = currentDate.toISOString().slice(0, 10); - - // 重置到中心位置(此时日期已更新,prev/next 已重新计算,且没有 transition) - translateX.value = -screenWidth.value; - baseTranslateX.value = -screenWidth.value; - - console.log(`日期切换:上一天,新日期:${selectedDate.value}`); - }, 0); // 一帧的时间,确保 transition 已禁用 - }, 0); // 与 transition 时间一致(0.3s) -}; - -// 滑动到后一天的位置(动画完成后更新日期) -const slideToNextDay = () => { - isAnimating.value = true; - // 从当前位置继续滑动到后一天的完整位置(0) - const targetX = -screenWidth.value; - translateX.value = targetX; - - // 等待动画完成(300ms,与 transition 时间一致) - setTimeout(() => { - // 滑动动画完成后,先暂时禁用 transition - isAnimating.value = false; - - // 在下一帧更新日期和重置位置(确保没有 transition 动画) - setTimeout(() => { - // 更新日期 - const currentDate = new Date(selectedDate.value); - currentDate.setDate(currentDate.getDate() + 1); - selectedDate.value = currentDate.toISOString().slice(0, 10); - - // 重置到中心位置(此时日期已更新,prev/next 已重新计算,且没有 transition) - translateX.value = -screenWidth.value; - baseTranslateX.value = -screenWidth.value; - - console.log(`日期切换:下一天,新日期:${selectedDate.value}`); - }, 16); // 一帧的时间,确保 transition 已禁用 - }, 300); // 与 transition 时间一致(0.3s) -}; - -// 监听日期变化,重置位置 -watch(selectedDate, () => { - if (!isDragging.value && !isAnimating.value) { - resetToCenter(); - } -}); - -// 组件挂载时初始化 -onMounted(() => { - initScreenWidth(); -}); - // 页面显示时处理从新建日程页面返回的数据 onShow(() => { // 从全局存储中读取新添加的日程数据 @@ -396,33 +170,5 @@ onShow(() => { margin-top: calc(var(--status-bar-height, 0) + 44px); } -.schedule-content { - width: 100%; - height: 100%; -} - :deep(.bottom-tabbar) { z-index: 1000 !important; } - -.schedule-timeline { - padding-bottom: 130rpx !important; -} - -.swipe-container { - position: relative; - width: 100%; - overflow: hidden; - touch-action: pan-y; /* 允许垂直滚动,但控制水平滑动 */ -} - -.swipe-wrapper { - display: flex; - width: 300%; /* 三个表格的宽度 */ - will-change: transform; /* 优化性能 */ -} - -.table-item { - flex: 0 0 33.333%; /* 每个表格占33.333% */ - width: 33.333%; - min-width: 0; -} \ No newline at end of file