diff --git a/app/src/main/java/com/gamedog/vididin/main/fragments/task/DayStatus.kt b/app/src/main/java/com/gamedog/vididin/main/fragments/task/DayStatus.kt index 5b5074a..59a4fd3 100644 --- a/app/src/main/java/com/gamedog/vididin/main/fragments/task/DayStatus.kt +++ b/app/src/main/java/com/gamedog/vididin/main/fragments/task/DayStatus.kt @@ -5,6 +5,7 @@ data class DayStatus( val day: Int, // 第几天 (1-7) val reward: String, // 奖励数值 ("100", "300"等) val isCompleted: Boolean = false, // 是否已完成 + val isPastDay: Boolean = false, val isToday: Boolean = false, // 是否是今天 val icon: String = if (isCompleted) "✓" else "G" // 图标 ) { diff --git a/app/src/main/java/com/gamedog/vididin/main/fragments/task/WeekStatusView.kt b/app/src/main/java/com/gamedog/vididin/main/fragments/task/WeekStatusView.kt index ffa3ebf..d0e85bf 100644 --- a/app/src/main/java/com/gamedog/vididin/main/fragments/task/WeekStatusView.kt +++ b/app/src/main/java/com/gamedog/vididin/main/fragments/task/WeekStatusView.kt @@ -8,6 +8,7 @@ import com.ama.core.common.util.dp import com.ama.core.common.util.sp import com.gamedog.vididin.R import android.graphics.* +import com.ama.core.architecture.BaseApp import java.util.* class WeekStatusView @JvmOverloads constructor( @@ -16,22 +17,24 @@ class WeekStatusView @JvmOverloads constructor( defStyleAttr: Int = 0 ) : View(context, attrs, defStyleAttr) { - // 默认颜色配置(匹配图片样式) - private var completedColor = Color.parseColor("#4CAF50") // 已完成绿色 - private var pendingColor = Color.parseColor("#FF9800") // 未完成橙色 - private var textColor = Color.parseColor("#757575") // 文字灰色 - private var rewardTextColor = Color.parseColor("#FF9800") // 奖励数值橙色 - private var todayHighlightColor = Color.parseColor("#4CAF50") // 今天高亮边框颜色 + private var currentDay = 1 + private var dayStatusList: List = emptyList() + private var completedColor = Color.parseColor("#4CAF50") + private var pendingColor = Color.parseColor("#FF9800") + private var dayColor = Color.parseColor("#FF999999") + private var dayPastColor = Color.parseColor("#FFD4D4D4") + private var rewardTextColor = Color.parseColor("#FF9800") + private var todayHighlightColor = Color.parseColor("#4CAF50") private var bgRectColor = Color.parseColor("#ffffedd7") - - // 默认尺寸配置 - private var circleRadius = 40f.dp.toFloat() - private var textSize = 12f.sp.toFloat() + private var circleRadius = 46.5F + private var dayTextSize = 12f.sp.toFloat() private var rewardTextSize = 14f.sp.toFloat() - private var itemSpacing = 16f.dp.toFloat() + private var HoriMagin = 5F.dp.toFloat() + private var vertiMagin = 5F.dp.toFloat() + private var componentGap = 15F.dp.toFloat() private var todayStrokeWidth = 3f.dp.toFloat() private var bgRectHeight = 10.dp.toFloat() @@ -49,16 +52,10 @@ class WeekStatusView @JvmOverloads constructor( isAntiAlias = true textAlign = Paint.Align.CENTER } - private val todayHighlightPaint = Paint().apply { - isAntiAlias = true - style = Paint.Style.STROKE - color = todayHighlightColor - strokeWidth = todayStrokeWidth.toFloat() - } - // 数据 - private var dayStatusList: List = emptyList() - private var currentDay = 1 + + + init { setupAttributes(attrs) @@ -70,19 +67,16 @@ class WeekStatusView @JvmOverloads constructor( completedColor = typedArray.getColor(R.styleable.WeekStatusView_completedColor, completedColor) pendingColor = typedArray.getColor(R.styleable.WeekStatusView_pendingColor, pendingColor) - textColor = typedArray.getColor(R.styleable.WeekStatusView_textColor, textColor) + dayColor = typedArray.getColor(R.styleable.WeekStatusView_textColor, dayColor) rewardTextColor = typedArray.getColor(R.styleable.WeekStatusView_rewardTextColor, rewardTextColor) todayHighlightColor = typedArray.getColor(R.styleable.WeekStatusView_todayHighlightColor, todayHighlightColor) circleRadius = typedArray.getDimension(R.styleable.WeekStatusView_circleRadius, circleRadius) - textSize = typedArray.getDimension(R.styleable.WeekStatusView_textSize, textSize) + dayTextSize = typedArray.getDimension(R.styleable.WeekStatusView_textSize, dayTextSize) rewardTextSize = typedArray.getDimension(R.styleable.WeekStatusView_rewardTextSize, rewardTextSize) - itemSpacing = typedArray.getDimension(R.styleable.WeekStatusView_itemSpacing, itemSpacing) + vertiMagin = typedArray.getDimension(R.styleable.WeekStatusView_itemSpacing, vertiMagin) todayStrokeWidth = typedArray.getDimension(R.styleable.WeekStatusView_todayStrokeWidth, todayStrokeWidth) - todayHighlightPaint.strokeWidth = todayStrokeWidth - todayHighlightPaint.color = todayHighlightColor - typedArray.recycle() } @@ -93,7 +87,7 @@ class WeekStatusView @JvmOverloads constructor( override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) { val desiredWidth = MeasureSpec.getSize(widthMeasureSpec) - val desiredHeight = (circleRadius * 2 + textSize * 3 + itemSpacing * 2).toInt() + val desiredHeight = (circleRadius * 2 + dayTextSize + rewardTextSize + vertiMagin * 2 + 2*componentGap).toInt() setMeasuredDimension( resolveSize(desiredWidth, widthMeasureSpec), @@ -103,95 +97,71 @@ class WeekStatusView @JvmOverloads constructor( override fun onDraw(canvas: Canvas) { super.onDraw(canvas) - if (dayStatusList.isEmpty()) return val totalWidth = measuredWidth.toFloat() - val totalHeight = measuredHeight.toFloat() - val totalItems = dayStatusList.size - val availableWidth = totalWidth - (itemSpacing * (totalItems - 1)) - val itemWidth = availableWidth / totalItems + val totalItemCount = dayStatusList.size + val itemHoriGapPixel = (totalWidth - 2 * circleRadius - 2 * HoriMagin) / (totalItemCount - 1) - // bg - canvas.drawRect(itemWidth/2, (totalHeight - bgRectHeight)/2, totalWidth - itemWidth/2, totalHeight - (totalHeight - bgRectHeight)/2, bgPaint) + // bg rect + val bgTop = vertiMagin + dayTextSize + componentGap + (circleRadius - bgRectHeight/2) + canvas.drawRect(circleRadius + HoriMagin, bgTop, + totalWidth - circleRadius - HoriMagin, bgTop + bgRectHeight, bgPaint) dayStatusList.forEachIndexed { index, dayStatus -> - val centerX = itemWidth / 2 + index * (itemWidth + itemSpacing) - drawDayStatus(canvas, dayStatus, centerX) + val centerX = HoriMagin + circleRadius + itemHoriGapPixel * index + drawDayStatusItem(canvas, dayStatus, centerX) } } - private fun drawDayStatus(canvas: Canvas, dayStatus: DayStatus, centerX: Float) { - val centerY = height / 2f - val circleCenterY = centerY - circleRadius + private fun drawDayStatusItem(canvas: Canvas, dayStatus: DayStatus, centerX: Float) { + // day text 'dia' + textPaint.color = if (dayStatus.isCompleted) dayPastColor else dayColor + textPaint.textSize = dayTextSize + canvas.drawText(dayStatus.displayText, centerX, vertiMagin + dayTextSize/2, textPaint) - // 绘制圆形背景 - circlePaint.color = if (dayStatus.isCompleted) completedColor else pendingColor - canvas.drawCircle(centerX, circleCenterY, circleRadius, circlePaint) + // icons + val iconRes = if (dayStatus.isCompleted) R.mipmap.task_week_view_done else R.mipmap.task_week_view_ongoing + canvas.drawBitmap(getBitmap(iconRes)!!, centerX - circleRadius, vertiMagin + dayTextSize + componentGap, circlePaint) - // 绘制图标(对勾或G) - textPaint.color = Color.WHITE - textPaint.textSize = circleRadius * 0.6f - val iconBounds = Rect() - textPaint.getTextBounds(dayStatus.icon, 0, dayStatus.icon.length, iconBounds) - val iconY = circleCenterY + (iconBounds.height() / 2) - iconBounds.bottom - canvas.drawText(dayStatus.icon, centerX, iconY, textPaint) - - // 绘制天数文字 (Dia X) - textPaint.color = textColor - textPaint.textSize = textSize - canvas.drawText(dayStatus.displayText, centerX, circleCenterY + circleRadius + textSize + 5, textPaint) - - // 绘制奖励数值 + // reward text textPaint.color = rewardTextColor textPaint.textSize = rewardTextSize - canvas.drawText(dayStatus.reward, centerX, circleCenterY + circleRadius + textSize + rewardTextSize + 15, textPaint) + canvas.drawText(dayStatus.reward, centerX, vertiMagin + dayTextSize + componentGap + 2*circleRadius + componentGap, textPaint) + } - // 如果是今天,绘制高亮边框 - if (dayStatus.isToday) { - canvas.drawCircle(centerX, circleCenterY, circleRadius + 2, todayHighlightPaint) + fun getBitmap(resId: Int): Bitmap? { + return try { + BitmapFactory.decodeResource(BaseApp.appContext().resources, resId) + } catch (e: Exception) { + e.printStackTrace() + null } } - // ==================== 公开API方法 ==================== - /** - * 更新显示的数据 - * @param data 新的天数状态列表 - */ + + // --------------------- public --------------------- fun updateData(data: List) { dayStatusList = data invalidate() } - /** - * 根据目标日期更新状态(自动计算完成状态) - * @param targetDate 目标日期 - */ fun updateForDate(targetDate: Date) { val targetDay = getDayOfWeekFromDate(targetDate) dayStatusList = generateWeekData(targetDay) invalidate() } - /** - * 刷新为当前日期 - */ fun refreshToCurrentDate() { updateForDate(Date()) } - /** - * 获取当前显示的数据 - */ fun getCurrentData(): List = dayStatusList - /** - * 获取当前高亮的天数(今天) - */ fun getCurrentDay(): Int = currentDay - // ==================== 工具方法 ==================== + private fun generateWeekData(targetDay: Int): List { val rewards = listOf("100", "300", "300", "500", "300", "300", "800") @@ -216,8 +186,6 @@ class WeekStatusView @JvmOverloads constructor( } private fun convertCalendarDayToWeekDay(calendarDay: Int): Int { - // Calendar: 周日=1, 周一=2, ..., 周六=7 - // 转换为: 周一=1, 周二=2, ..., 周日=7 return if (calendarDay == 1) 7 else calendarDay - 1 } diff --git a/app/src/main/res/layout/vididinapp_feature_message_fragment_message.xml b/app/src/main/res/layout/vididinapp_feature_message_fragment_message.xml index 388235e..360ff23 100644 --- a/app/src/main/res/layout/vididinapp_feature_message_fragment_message.xml +++ b/app/src/main/res/layout/vididinapp_feature_message_fragment_message.xml @@ -346,14 +346,14 @@ android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="vertical" + android:background="@drawable/vididinapp_feature_message_bg_task_login" android:layout_marginTop="10dp"> + android:padding="10dp"> + />