refactor: 清理无效 ProGuard 规则、调试日志,trace 解耦 VM
P0 正确性与工程卫生修复:
- 删除 core/proguard-rules.pro 中全部无效的 -keepclassmembers 规则
(LunarCache.getOrCompute 实为实例 suspend 方法,generateMonthDays 实为
private,签名均不匹配,属 placebo);同时移除 core/build.gradle.kts
release block 内重复的 consumerProguardFiles 声明
- 将 7 处 composeTrace 调用从 CalendarViewModel 移至 Compose 层
(MenuItem.onClick / onMonthClick / BottomCard 回调),VM 不再依赖
android.os.Trace,可在纯 JVM 环境测试无需兜底
- 删除 CalendarViewModel 与 4 个 UI 文件中约 30 处 logd 调用及其辅助
变量/ SideEffect/ DisposableEffect (AnimLog.kt 工具函数保留)
- 删除 CalendarViewModel.getIsoWeekNumber 不可达的 weekNumber < 1 递归分支
- 修正 MainActivity.kt setContent 块缩进错位
- 同步 README: sketch 渲染 GIF→动画 WebP,补提 :macrobenchmark 模块;
删除 AGENTS.md 顶部过时的「README 与实际不符」注释
验证: spotlessApply UP-TO-DATE, testDebugUnitTest 全过,
assembleDebug + assembleRelease (R8) 均成功
This commit is contained in:
parent
ef785a3ca7
commit
564e4e3960
@ -2,8 +2,6 @@
|
||||
|
||||
纯 Android + Jetpack Compose 日历应用。功能:农历/节气/节日、个人班次排期(WORK/OFF 循环)、月/周/年三视图。
|
||||
|
||||
> **README 与实际不符**:README 提及 "Kotlin Multiplatform / iOS",实际为纯 Android 项目。模块名为 `:core` 和 `:app`,无 `:shared` 或 `:androidApp`。
|
||||
|
||||
## 模块结构
|
||||
|
||||
| 模块 | 类型 | 职责 |
|
||||
|
||||
@ -19,8 +19,8 @@
|
||||
- Kotlin 2.3 · Jetpack Compose · Material 3
|
||||
- `kotlinx-datetime` 处理所有日期逻辑
|
||||
- `tyme4kt` 提供农历、节气与传统节日
|
||||
- `sketch` 渲染 GIF 动画
|
||||
- 双模块:`:core`(UI + 逻辑) · `:app`(薄壳)
|
||||
- `sketch` 渲染动画 WebP
|
||||
- 三模块:`:core`(UI + 逻辑) · `:app`(薄壳) · `:macrobenchmark`(Baseline Profile 生成)
|
||||
|
||||
## 构建
|
||||
|
||||
|
||||
@ -35,7 +35,6 @@ android {
|
||||
}
|
||||
release {
|
||||
isMinifyEnabled = false
|
||||
consumerProguardFiles("proguard-rules.pro")
|
||||
buildConfigField("boolean", "ENABLE_TRACE", "false")
|
||||
}
|
||||
create("trace") {
|
||||
|
||||
28
core/proguard-rules.pro
vendored
28
core/proguard-rules.pro
vendored
@ -1,34 +1,6 @@
|
||||
# Baseline Profiles 保留规则:确保方法名不被 R8 混淆,使 profile 规则匹配正确
|
||||
-keepattributes SourceFile,LineNumberTable
|
||||
|
||||
# ========== 启动热点路径保留 ==========
|
||||
|
||||
# DayCell — 启动最热点
|
||||
-keepclassmembers class plus.rua.project.ui.DayCellKt {
|
||||
public static void DayCell(...);
|
||||
}
|
||||
|
||||
# LunarCache — 日期计算缓存
|
||||
-keepclassmembers class plus.rua.project.LunarCache {
|
||||
public static plus.rua.project.DayCellInfo getOrCompute(kotlinx.datetime.LocalDate);
|
||||
public static java.lang.String formatLunarDate(kotlinx.datetime.LocalDate);
|
||||
public static void precompute(...);
|
||||
}
|
||||
|
||||
# DayCellInfo 数据类
|
||||
-keepclassmembers class plus.rua.project.DayCellInfo {
|
||||
public java.lang.String getAnnotationText();
|
||||
public boolean getIsAnnotationHighlight();
|
||||
public java.lang.String getHolidayBadge();
|
||||
public java.lang.String getLunarMonthName();
|
||||
}
|
||||
|
||||
# CalendarMonthPage
|
||||
-keepclassmembers class plus.rua.project.ui.CalendarMonthPageKt {
|
||||
public static void CalendarMonthPage(...);
|
||||
public static java.util.List generateMonthDays(...);
|
||||
}
|
||||
|
||||
# ========== 第三方库保留 ==========
|
||||
-keep class kotlinx.datetime.** { *; }
|
||||
-keep class cn.tyme.** { *; }
|
||||
|
||||
@ -21,11 +21,8 @@ import kotlinx.datetime.plus
|
||||
import kotlinx.datetime.todayIn
|
||||
import plus.rua.project.ui.COLLAPSE_THRESHOLD
|
||||
import plus.rua.project.ui.getMonthGridInfo
|
||||
import plus.rua.project.util.logd
|
||||
import kotlin.time.Clock
|
||||
|
||||
private const val TAG_VM = "CalendarExpand"
|
||||
|
||||
/**
|
||||
* 日历日期数据,用于网格单元格渲染。
|
||||
*
|
||||
@ -170,23 +167,11 @@ class CalendarViewModel(
|
||||
* 当前视图被直接移除;动画只作用在目标视图的 scale/alpha 上。
|
||||
*/
|
||||
fun toggleYearView() {
|
||||
val t0 = System.nanoTime()
|
||||
if (_isYearView.value) {
|
||||
logd(TAG_VM, "[toggleYearView] ===== START Year→Month t=$t0 =====")
|
||||
composeTraceBeginSection("YearView→MonthView")
|
||||
_isYearView.value = false
|
||||
logd(TAG_VM, "[toggleYearView] isYearView=false dt=${(System.nanoTime() - t0) / 1_000_000}ms")
|
||||
composeTraceEndSection()
|
||||
logd(TAG_VM, "[toggleYearView] ===== END Year→Month total=${(System.nanoTime() - t0) / 1_000_000}ms =====")
|
||||
} else {
|
||||
logd(TAG_VM, "[toggleYearView] ===== START Month→Year t=$t0 =====")
|
||||
composeTraceBeginSection("MonthView→YearView")
|
||||
_yearViewYear.value = _selectedDate.value.year
|
||||
logd(TAG_VM, "[toggleYearView] yearViewYear=${_yearViewYear.value} dt=${(System.nanoTime() - t0) / 1_000_000}ms")
|
||||
_isYearView.value = true
|
||||
logd(TAG_VM, "[toggleYearView] isYearView=true dt=${(System.nanoTime() - t0) / 1_000_000}ms")
|
||||
composeTraceEndSection()
|
||||
logd(TAG_VM, "[toggleYearView] ===== END Month→Year total=${(System.nanoTime() - t0) / 1_000_000}ms =====")
|
||||
}
|
||||
}
|
||||
|
||||
@ -201,18 +186,10 @@ class CalendarViewModel(
|
||||
* 从年视图选择月份后返回月视图。
|
||||
*/
|
||||
fun selectMonthFromYearView(month: Int) {
|
||||
val t0 = System.nanoTime()
|
||||
logd(TAG_VM, "[selectMonthFromYearView] ===== START month=$month t=$t0 =====")
|
||||
composeTraceBeginSection("YearView:SelectMonth")
|
||||
val date = if (_yearViewYear.value == today.year && today.month.number == month) today
|
||||
else LocalDate(_yearViewYear.value, Month(month), 1)
|
||||
logd(TAG_VM, "[selectMonthFromYearView] targetDate=$date dt=${(System.nanoTime() - t0) / 1_000_000}ms")
|
||||
_selectedDate.value = date
|
||||
logd(TAG_VM, "[selectMonthFromYearView] selectedDate set dt=${(System.nanoTime() - t0) / 1_000_000}ms")
|
||||
_isYearView.value = false
|
||||
logd(TAG_VM, "[selectMonthFromYearView] isYearView=false dt=${(System.nanoTime() - t0) / 1_000_000}ms")
|
||||
composeTraceEndSection()
|
||||
logd(TAG_VM, "[selectMonthFromYearView] ===== END total=${(System.nanoTime() - t0) / 1_000_000}ms =====")
|
||||
}
|
||||
|
||||
fun incrementYear() {
|
||||
@ -233,9 +210,7 @@ class CalendarViewModel(
|
||||
* @param delta 拖拽增量,已归一化到 [0,1] 区间
|
||||
*/
|
||||
fun onDrag(delta: Float) {
|
||||
composeTraceBeginSection("VM:collapseProgress:onDrag")
|
||||
_collapseProgress.value = (_collapseProgress.value + delta).coerceIn(0f, 1f)
|
||||
composeTraceEndSection()
|
||||
}
|
||||
|
||||
/**
|
||||
@ -244,7 +219,6 @@ class CalendarViewModel(
|
||||
* 拖拽超过阈值时自动折叠到周视图,否则回弹到月视图。
|
||||
*/
|
||||
fun onDragEnd() {
|
||||
composeTraceBeginSection("VM:collapseProgress:onDragEnd")
|
||||
val progress = _collapseProgress.value
|
||||
if (progress > COLLAPSE_THRESHOLD) {
|
||||
_isCollapsed.value = true
|
||||
@ -253,7 +227,6 @@ class CalendarViewModel(
|
||||
_isCollapsed.value = false
|
||||
_collapseProgress.value = 0f
|
||||
}
|
||||
composeTraceEndSection()
|
||||
}
|
||||
|
||||
/**
|
||||
@ -262,11 +235,7 @@ class CalendarViewModel(
|
||||
* @param delta 拖拽增量,已归一化到 [0,1] 区间
|
||||
*/
|
||||
fun onExpandDrag(delta: Float) {
|
||||
composeTraceBeginSection("VM:collapseProgress:onExpandDrag")
|
||||
val old = _collapseProgress.value
|
||||
_collapseProgress.value = (_collapseProgress.value + delta).coerceIn(0f, 1f)
|
||||
logd(TAG_VM, "onExpandDrag: delta=$delta old=$old new=${_collapseProgress.value}")
|
||||
composeTraceEndSection()
|
||||
}
|
||||
|
||||
/**
|
||||
@ -275,19 +244,14 @@ class CalendarViewModel(
|
||||
* 下拉超过阈值时自动展开到月视图,否则回弹到周视图。
|
||||
*/
|
||||
fun onExpandDragEnd() {
|
||||
composeTraceBeginSection("VM:collapseProgress:onExpandDragEnd")
|
||||
val progress = _collapseProgress.value
|
||||
val result = if (progress < (1 - COLLAPSE_THRESHOLD)) {
|
||||
if (progress < (1 - COLLAPSE_THRESHOLD)) {
|
||||
_isCollapsed.value = false
|
||||
_collapseProgress.value = 0f
|
||||
"EXPANDED"
|
||||
} else {
|
||||
_isCollapsed.value = true
|
||||
_collapseProgress.value = 1f
|
||||
"COLLAPSED (bounce back)"
|
||||
}
|
||||
logd(TAG_VM, "onExpandDragEnd: progress=$progress threshold=${1 - COLLAPSE_THRESHOLD} result=$result")
|
||||
composeTraceEndSection()
|
||||
}
|
||||
|
||||
/**
|
||||
@ -302,9 +266,7 @@ class CalendarViewModel(
|
||||
val week1Monday = jan4.minus(DatePeriod(days = jan4DayOfWeek))
|
||||
val diff = week1Monday.daysUntil(date)
|
||||
val weekNumber = diff / 7 + 1
|
||||
return if (weekNumber < 1) {
|
||||
getIsoWeekNumber(LocalDate(date.year - 1, 12, 28))
|
||||
} else if (weekNumber > getIsoWeeksInYear(date.year)) {
|
||||
return if (weekNumber > getIsoWeeksInYear(date.year)) {
|
||||
1
|
||||
} else {
|
||||
weekNumber
|
||||
@ -325,14 +287,16 @@ class CalendarViewModel(
|
||||
*
|
||||
* 网格行数按实际需要计算(4/5/6行),每行7格,首行从该月1号所在周的周一开始。
|
||||
*
|
||||
* 注意:此方法当前无 UI 调用方,UI 层使用 [CalendarMonthPage] 内的 generateMonthDays;
|
||||
* 保留此方法供测试覆盖和未来复用(含 isToday/isSelected 字段语义)。
|
||||
*
|
||||
* @param year 年份
|
||||
* @param month 月份(1-12)
|
||||
* @return 日历网格列表,每项包含日期、是否当月、是否今天、是否选中
|
||||
*/
|
||||
fun getMonthDays(year: Int, month: Int): List<CalendarDay> {
|
||||
composeTraceBeginSection("getMonthDays:$year-$month")
|
||||
val info = getMonthGridInfo(year, month)
|
||||
val result = (0 until info.totalDays).map { i ->
|
||||
return (0 until info.totalDays).map { i ->
|
||||
val date = info.startDate.plus(DatePeriod(days = i))
|
||||
CalendarDay(
|
||||
date = date,
|
||||
@ -341,7 +305,5 @@ class CalendarViewModel(
|
||||
isSelected = date == selectedDate.value
|
||||
)
|
||||
}
|
||||
composeTraceEndSection()
|
||||
return result
|
||||
}
|
||||
}
|
||||
|
||||
@ -23,7 +23,6 @@ import androidx.compose.ui.unit.dp
|
||||
import androidx.compose.ui.zIndex
|
||||
import plus.rua.project.composeTraceBeginSection
|
||||
import plus.rua.project.composeTraceEndSection
|
||||
import plus.rua.project.util.logd
|
||||
import kotlinx.datetime.DatePeriod
|
||||
import kotlinx.datetime.LocalDate
|
||||
import kotlinx.datetime.Month
|
||||
@ -34,8 +33,6 @@ import plus.rua.project.DayCellInfo
|
||||
import plus.rua.project.LunarCache
|
||||
import plus.rua.project.ShiftKind
|
||||
|
||||
private const val TAG_CMP = "CalendarExpandAnim"
|
||||
|
||||
|
||||
/**
|
||||
* 月度日历网格页面,支持两阶段折叠动画。
|
||||
@ -110,16 +107,6 @@ fun CalendarMonthPage(
|
||||
weeks.indexOfFirst { week -> week.any { it.date == selectedDate } }
|
||||
}
|
||||
|
||||
// 全局动画参数日志(每次重组)
|
||||
val pageFrameNs = System.nanoTime()
|
||||
val totalCells = weeks.size * 7
|
||||
logd(TAG_CMP) {
|
||||
"Page[$year-$month]: anchorIndex=$anchorIndex weeksSize=${weeks.size} totalCells=$totalCells " +
|
||||
"phase1End=${if (anchorIndex > 0 && weeks.size > 1) anchorIndex.toFloat() / (weeks.size - 1) else 0f} " +
|
||||
"effectiveWeeks=$effectiveWeeks rowHeightPx=$rowHeightPx " +
|
||||
"collapseProgress=$collapseProgress lunarMapSize=${lunarDataMap.size} frameNs=$pageFrameNs"
|
||||
}
|
||||
|
||||
val totalHeightDp = if (rowHeightPx > 0) {
|
||||
val h = rowHeightPx.toFloat()
|
||||
val totalPx = h * (1 + (effectiveWeeks - 1) * (1f - collapseProgress))
|
||||
@ -216,17 +203,6 @@ private fun WeekRow(
|
||||
else -> 1f
|
||||
}
|
||||
|
||||
val frameTimeNs = System.nanoTime()
|
||||
logd(TAG_CMP) {
|
||||
"WeekRow[$weekIndex]: " +
|
||||
"isAnchor=$isAnchor isAbove=$isAbove isBelow=$isBelow " +
|
||||
"phase1=$phase1 phase2=$phase2 phase1End=$phase1End " +
|
||||
"belowRowsHeight=$belowRowsHeight rowHeightPx=$rowHeightPx " +
|
||||
"yOffsetPx=$yOffsetPx rowAlpha=$rowAlpha " +
|
||||
"collapseProgress=$collapseProgress " +
|
||||
"frameNs=$frameTimeNs"
|
||||
}
|
||||
|
||||
if (rowAlpha > 0.01f) {
|
||||
Row(
|
||||
modifier = Modifier
|
||||
|
||||
@ -49,7 +49,6 @@ import androidx.compose.material3.MaterialTheme
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.LaunchedEffect
|
||||
import androidx.compose.runtime.SideEffect
|
||||
import androidx.compose.runtime.collectAsState
|
||||
import androidx.compose.runtime.getValue
|
||||
import androidx.compose.runtime.mutableIntStateOf
|
||||
@ -85,7 +84,6 @@ import plus.rua.project.composeTraceEndSection
|
||||
import kotlin.math.abs
|
||||
import kotlin.time.Clock
|
||||
import androidx.lifecycle.viewmodel.compose.viewModel
|
||||
import plus.rua.project.util.logd
|
||||
|
||||
/**
|
||||
* 日历主界面,包含月/周视图切换、折叠动画和年视图转场。
|
||||
@ -120,14 +118,6 @@ fun CalendarMonthView(
|
||||
animationSpec = spring(stiffness = Spring.StiffnessMedium),
|
||||
label = "collapseProgress"
|
||||
)
|
||||
var lastLoggedCollapse by remember { mutableStateOf(-1f) }
|
||||
SideEffect {
|
||||
if (kotlin.math.abs(lastLoggedCollapse - collapseProgress) > 0.001f) {
|
||||
lastLoggedCollapse = collapseProgress
|
||||
logd("AnimLog", "[Collapse] target=$collapseProgress animated=$animatedCollapseProgress isCollapsed=$isCollapsed")
|
||||
}
|
||||
logd("AnimLog", "[MonthView] isYearView=$isYearView isCollapsed=$isCollapsed collapseProgress=$collapseProgress animated=$animatedCollapseProgress selectedDate=$selectedDate yearViewYear=$yearViewYear")
|
||||
}
|
||||
|
||||
val density = LocalDensity.current
|
||||
val coroutineScope = rememberCoroutineScope()
|
||||
@ -182,13 +172,6 @@ fun CalendarMonthView(
|
||||
screenWidthPx = size.width
|
||||
}
|
||||
) {
|
||||
var lastLoggedTargetState by remember { mutableStateOf(false) }
|
||||
SideEffect {
|
||||
if (lastLoggedTargetState != isYearView) {
|
||||
lastLoggedTargetState = isYearView
|
||||
logd("AnimLog", "[AnimatedContent] ★ targetState CHANGE isYearView=$isYearView t=${System.nanoTime()}")
|
||||
}
|
||||
}
|
||||
AnimatedContent(
|
||||
targetState = isYearView,
|
||||
label = "month_year_transition",
|
||||
@ -206,13 +189,6 @@ fun CalendarMonthView(
|
||||
modifier = Modifier.fillMaxSize()
|
||||
) { yearViewActive ->
|
||||
if (!yearViewActive) {
|
||||
androidx.compose.runtime.DisposableEffect(Unit) {
|
||||
val t = System.nanoTime()
|
||||
logd("AnimLog", "[MonthView] ★★★ ENTER composable t=$t")
|
||||
onDispose {
|
||||
logd("AnimLog", "[MonthView] ★★★ LEAVE composable alive=${(System.nanoTime() - t) / 1_000_000}ms")
|
||||
}
|
||||
}
|
||||
composeTraceBeginSection("MonthView:Compose")
|
||||
composeTraceBeginSection("CalendarPagerArea")
|
||||
val layoutReady = rowHeightPx > 0
|
||||
@ -285,13 +261,6 @@ fun CalendarMonthView(
|
||||
composeTraceEndSection()
|
||||
composeTraceEndSection()
|
||||
} else {
|
||||
androidx.compose.runtime.DisposableEffect(Unit) {
|
||||
val t = System.nanoTime()
|
||||
logd("AnimLog", "[YearView] ★★★ ENTER composable t=$t")
|
||||
onDispose {
|
||||
logd("AnimLog", "[YearView] ★★★ LEAVE composable alive=${(System.nanoTime() - t) / 1_000_000}ms")
|
||||
}
|
||||
}
|
||||
composeTraceBeginSection("YearView:Compose")
|
||||
Column(
|
||||
modifier = Modifier
|
||||
@ -310,13 +279,6 @@ fun CalendarMonthView(
|
||||
}
|
||||
}
|
||||
)
|
||||
var lastLoggedYearPage by remember { mutableIntStateOf(-1) }
|
||||
SideEffect {
|
||||
if (lastLoggedYearPage != yearPagerState.currentPage) {
|
||||
lastLoggedYearPage = yearPagerState.currentPage
|
||||
logd("AnimLog", "[YearPager] page=${yearPagerState.currentPage} settledPage=${yearPagerState.settledPage} offset=${yearPagerState.currentPageOffsetFraction}")
|
||||
}
|
||||
}
|
||||
HorizontalPager(
|
||||
state = yearPagerState,
|
||||
beyondViewportPageCount = 0,
|
||||
@ -329,26 +291,21 @@ fun CalendarMonthView(
|
||||
val pageYear = remember(page, yearViewYear, yearPagerState.settledPage) {
|
||||
yearViewYear + (page - yearPagerState.settledPage)
|
||||
}
|
||||
val isCurrentPage = page == yearPagerState.currentPage
|
||||
if (isCurrentPage) {
|
||||
logd("AnimLog") { "[YearPager] Compose page=$page year=$pageYear" }
|
||||
}
|
||||
YearGridView(
|
||||
year = pageYear,
|
||||
selectedMonth = if (pageYear == currentYear) currentMonth else 0,
|
||||
today = today,
|
||||
onMonthClick = { month ->
|
||||
val clickT = System.nanoTime()
|
||||
logd("AnimLog") { "[YearGridView] MonthClick month=$month year=$pageYear t=$clickT" }
|
||||
composeTraceBeginSection("YearView:SelectMonth")
|
||||
viewModel.selectMonthFromYearView(month)
|
||||
val targetPage = yearMonthToPage(
|
||||
yearViewYear, month,
|
||||
today.year, today.month.number
|
||||
)
|
||||
if (targetPage != pagerState.currentPage) {
|
||||
logd("AnimLog") { "[YearPager] scrollToPage target=$targetPage" }
|
||||
coroutineScope.launch { pagerState.scrollToPage(targetPage) }
|
||||
}
|
||||
composeTraceEndSection()
|
||||
},
|
||||
modifier = Modifier
|
||||
)
|
||||
@ -426,7 +383,11 @@ fun CalendarMonthView(
|
||||
selected = !isYearView,
|
||||
onClick = {
|
||||
isMenuExpanded = false
|
||||
if (isYearView) viewModel.toggleYearView()
|
||||
if (isYearView) {
|
||||
composeTraceBeginSection("YearView→MonthView")
|
||||
viewModel.toggleYearView()
|
||||
composeTraceEndSection()
|
||||
}
|
||||
}
|
||||
)
|
||||
MenuItem(
|
||||
@ -434,7 +395,11 @@ fun CalendarMonthView(
|
||||
selected = isYearView,
|
||||
onClick = {
|
||||
isMenuExpanded = false
|
||||
if (!isYearView) viewModel.toggleYearView()
|
||||
if (!isYearView) {
|
||||
composeTraceBeginSection("MonthView→YearView")
|
||||
viewModel.toggleYearView()
|
||||
composeTraceEndSection()
|
||||
}
|
||||
}
|
||||
)
|
||||
HorizontalDivider(
|
||||
@ -492,13 +457,12 @@ private fun CalendarPagerArea(
|
||||
pagerState: PagerState,
|
||||
modifier: Modifier = Modifier
|
||||
) {
|
||||
val t0 = System.nanoTime()
|
||||
val density = LocalDensity.current
|
||||
|
||||
val interpolatedWeeks by remember {
|
||||
derivedStateOf {
|
||||
val fraction = pagerState.currentPageOffsetFraction
|
||||
val result = if (abs(fraction) > OFFSET_FRACTION_THRESHOLD) {
|
||||
if (abs(fraction) > OFFSET_FRACTION_THRESHOLD) {
|
||||
val cp = pagerState.currentPage
|
||||
val baseWeeks = calculateWeeksCountForPage(cp, today)
|
||||
val targetPage = cp + if (fraction > 0) 1 else -1
|
||||
@ -507,8 +471,6 @@ private fun CalendarPagerArea(
|
||||
} else {
|
||||
calculateWeeksCountForPage(pagerState.currentPage, today).toFloat()
|
||||
}
|
||||
logd("AnimLog", "[PagerArea] interpolatedWeeks=$result fraction=$fraction page=${pagerState.currentPage}")
|
||||
result
|
||||
}
|
||||
}
|
||||
|
||||
@ -532,8 +494,6 @@ private fun CalendarPagerArea(
|
||||
}
|
||||
} else 0
|
||||
|
||||
logd("AnimLog", "[PagerArea] gridHeightPx=$gridHeightPx effectiveRowHeightPx=$effectiveRowHeightPx effectiveWeeks=$effectiveWeeks collapseProgress=$collapseProgress screenW=$screenWidthPx rowH=$rowHeightPx dt=${(System.nanoTime() - t0) / 1_000_000}ms")
|
||||
|
||||
val pagerModifier = if (rowHeightPx > 0 && gridHeightPx > 0) {
|
||||
Modifier
|
||||
.height(with(density) { gridHeightPx.toDp() })
|
||||
@ -597,10 +557,26 @@ private fun BottomCardArea(
|
||||
selectedDate = uiState.selectedDate,
|
||||
today = today,
|
||||
shiftKind = shiftKind,
|
||||
onDrag = { delta -> viewModel.onDrag(delta) },
|
||||
onDragEnd = { viewModel.onDragEnd() },
|
||||
onExpandDrag = { delta -> viewModel.onExpandDrag(delta) },
|
||||
onExpandDragEnd = { viewModel.onExpandDragEnd() },
|
||||
onDrag = { delta ->
|
||||
composeTraceBeginSection("VM:collapseProgress:onDrag")
|
||||
viewModel.onDrag(delta)
|
||||
composeTraceEndSection()
|
||||
},
|
||||
onDragEnd = {
|
||||
composeTraceBeginSection("VM:collapseProgress:onDragEnd")
|
||||
viewModel.onDragEnd()
|
||||
composeTraceEndSection()
|
||||
},
|
||||
onExpandDrag = { delta ->
|
||||
composeTraceBeginSection("VM:collapseProgress:onExpandDrag")
|
||||
viewModel.onExpandDrag(delta)
|
||||
composeTraceEndSection()
|
||||
},
|
||||
onExpandDragEnd = {
|
||||
composeTraceBeginSection("VM:collapseProgress:onExpandDragEnd")
|
||||
viewModel.onExpandDragEnd()
|
||||
composeTraceEndSection()
|
||||
},
|
||||
dragRangePx = dragRangePx,
|
||||
modifier = modifier
|
||||
.offset(y = with(density) { (slideProgress * 300).dp })
|
||||
|
||||
@ -5,19 +5,15 @@ import androidx.compose.foundation.pager.PagerDefaults
|
||||
import androidx.compose.foundation.pager.PagerState
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.LaunchedEffect
|
||||
import androidx.compose.runtime.SideEffect
|
||||
import androidx.compose.runtime.derivedStateOf
|
||||
import androidx.compose.runtime.getValue
|
||||
import androidx.compose.runtime.mutableIntStateOf
|
||||
import androidx.compose.runtime.remember
|
||||
import androidx.compose.runtime.rememberCoroutineScope
|
||||
import androidx.compose.runtime.setValue
|
||||
import androidx.compose.runtime.snapshotFlow
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.platform.testTag
|
||||
import plus.rua.project.composeTraceBeginSection
|
||||
import plus.rua.project.composeTraceEndSection
|
||||
import plus.rua.project.util.logd
|
||||
import androidx.compose.ui.draw.alpha
|
||||
import kotlinx.coroutines.flow.drop
|
||||
import kotlinx.coroutines.launch
|
||||
@ -80,14 +76,6 @@ fun CalendarPager(
|
||||
derivedStateOf { pagerState.currentPage }
|
||||
}
|
||||
|
||||
var lastLoggedPage by remember { mutableIntStateOf(-1) }
|
||||
SideEffect {
|
||||
if (lastLoggedPage != pagerState.currentPage) {
|
||||
lastLoggedPage = pagerState.currentPage
|
||||
logd("AnimLog", "[CalendarPager] page=${pagerState.currentPage} settledPage=${pagerState.settledPage} offsetFraction=${pagerState.currentPageOffsetFraction}")
|
||||
}
|
||||
}
|
||||
|
||||
HorizontalPager(
|
||||
state = pagerState,
|
||||
beyondViewportPageCount = 0,
|
||||
@ -102,9 +90,6 @@ fun CalendarPager(
|
||||
pageOffset
|
||||
}
|
||||
val (year, month) = pageToYearMonth(page, initialYear, initialMonth)
|
||||
if (isCurrentPage) {
|
||||
logd("AnimLog", "[CalendarPager] Compose page=$page ($year-$month) alpha=$alpha pageOffset=$pageOffset")
|
||||
}
|
||||
composeTraceBeginSection("CalendarPager:Page:$year-$month")
|
||||
CalendarMonthPage(
|
||||
year = year,
|
||||
@ -112,7 +97,6 @@ fun CalendarPager(
|
||||
selectedDate = selectedDate,
|
||||
today = today,
|
||||
onDateClick = { date ->
|
||||
val clickT = System.nanoTime()
|
||||
onDateClick(date)
|
||||
// 点击跨月日期时,滚动到该月对应的页
|
||||
val clickedYear = date.year
|
||||
@ -121,7 +105,6 @@ fun CalendarPager(
|
||||
val targetPage =
|
||||
yearMonthToPage(clickedYear, clickedMonth, initialYear, initialMonth)
|
||||
if (targetPage != pagerState.currentPage) {
|
||||
logd("AnimLog", "[CalendarPager] Cross-month click date=$date targetPage=$targetPage t=$clickT")
|
||||
coroutineScope.launch {
|
||||
pagerState.animateScrollToPage(targetPage)
|
||||
}
|
||||
|
||||
@ -23,11 +23,8 @@ import androidx.compose.material3.MaterialTheme
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.getValue
|
||||
import androidx.compose.runtime.mutableStateOf
|
||||
import androidx.compose.runtime.produceState
|
||||
import androidx.compose.runtime.remember
|
||||
import androidx.compose.runtime.setValue
|
||||
import plus.rua.project.util.logd
|
||||
import androidx.compose.ui.Alignment
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.draw.clip
|
||||
@ -82,14 +79,6 @@ fun YearGridView(
|
||||
onMonthClick: (Int) -> Unit,
|
||||
modifier: Modifier = Modifier
|
||||
) {
|
||||
val enterT = System.nanoTime()
|
||||
logd("AnimLog", "[YearGridView] ★★★ ENTER year=$year selectedMonth=$selectedMonth t=$enterT")
|
||||
androidx.compose.runtime.DisposableEffect(year) {
|
||||
logd("AnimLog", "[YearGridView] DisposableEffect attached year=$year")
|
||||
onDispose {
|
||||
logd("AnimLog", "[YearGridView] ★★★ LEAVE year=$year alive=${(System.nanoTime() - enterT) / 1_000_000}ms")
|
||||
}
|
||||
}
|
||||
composeTraceBeginSection("YearGridView:$year")
|
||||
|
||||
// P0-F: 主题色在 YearGridView 级别一次性读取并缓存
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user