Skip to content

Commit

Permalink
add date to statistics detail records filter
Browse files Browse the repository at this point in the history
  • Loading branch information
Razeeman committed Sep 29, 2024
1 parent 298bbfa commit 901a7e8
Show file tree
Hide file tree
Showing 57 changed files with 598 additions and 222 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,13 @@ package com.example.util.simpletimetracker.core.extension
import com.example.util.simpletimetracker.core.mapper.TimeMapper
import com.example.util.simpletimetracker.core.viewData.ChangeRecordDateTimeState
import com.example.util.simpletimetracker.domain.model.Range
import com.example.util.simpletimetracker.domain.model.RangeLength
import com.example.util.simpletimetracker.domain.model.RecordsFilter
import com.example.util.simpletimetracker.feature_base_adapter.runningRecord.GoalTimeViewData
import com.example.util.simpletimetracker.feature_views.viewData.RecordTypeIcon
import com.example.util.simpletimetracker.navigation.params.screen.ChangeRecordDateTimeStateParams
import com.example.util.simpletimetracker.navigation.params.screen.ChangeRunningRecordParams
import com.example.util.simpletimetracker.navigation.params.screen.RangeLengthParams
import com.example.util.simpletimetracker.navigation.params.screen.RangeParams
import com.example.util.simpletimetracker.navigation.params.screen.RecordTypeIconParams
import com.example.util.simpletimetracker.navigation.params.screen.RecordsFilterParam
Expand Down Expand Up @@ -98,7 +100,7 @@ fun RecordsFilterParam.toModel(): RecordsFilter {
is RecordsFilterParam.Activity -> RecordsFilter.Activity(typeIds)
is RecordsFilterParam.Category -> RecordsFilter.Category(items.map { it.toModel() })
is RecordsFilterParam.Comment -> RecordsFilter.Comment(items.map { it.toModel() })
is RecordsFilterParam.Date -> RecordsFilter.Date(Range(rangeStart, rangeEnd))
is RecordsFilterParam.Date -> RecordsFilter.Date(range.toModel(), position)
is RecordsFilterParam.SelectedTags -> RecordsFilter.SelectedTags(items.map { it.toModel() })
is RecordsFilterParam.FilteredTags -> RecordsFilter.FilteredTags(items.map { it.toModel() })
is RecordsFilterParam.ManuallyFiltered -> RecordsFilter.ManuallyFiltered(recordIds)
Expand All @@ -115,7 +117,7 @@ fun RecordsFilter.toParams(): RecordsFilterParam {
is RecordsFilter.Activity -> RecordsFilterParam.Activity(typeIds)
is RecordsFilter.Category -> RecordsFilterParam.Category(items.map { it.toParams() })
is RecordsFilter.Comment -> RecordsFilterParam.Comment(items.map { it.toParams() })
is RecordsFilter.Date -> RecordsFilterParam.Date(range.timeStarted, range.timeEnded)
is RecordsFilter.Date -> RecordsFilterParam.Date(range.toParams(), position)
is RecordsFilter.SelectedTags -> RecordsFilterParam.SelectedTags(items.map { it.toParams() })
is RecordsFilter.FilteredTags -> RecordsFilterParam.FilteredTags(items.map { it.toParams() })
is RecordsFilter.ManuallyFiltered -> RecordsFilterParam.ManuallyFiltered(recordIds)
Expand Down Expand Up @@ -168,3 +170,36 @@ fun RecordsFilter.TagItem.toParams(): RecordsFilterParam.TagItem {
is RecordsFilter.TagItem.Untagged -> RecordsFilterParam.TagItem.Untagged
}
}

fun RangeLengthParams.toModel(): RangeLength {
return when (this) {
is RangeLengthParams.Day -> RangeLength.Day
is RangeLengthParams.Week -> RangeLength.Week
is RangeLengthParams.Month -> RangeLength.Month
is RangeLengthParams.Year -> RangeLength.Year
is RangeLengthParams.All -> RangeLength.All
is RangeLengthParams.Custom -> Range(
timeStarted = start, timeEnded = end,
).let(RangeLength::Custom)
is RangeLengthParams.Last -> RangeLength.Last(
days = days,
)
}
}

fun RangeLength.toParams(): RangeLengthParams {
return when (this) {
is RangeLength.Day -> RangeLengthParams.Day
is RangeLength.Week -> RangeLengthParams.Week
is RangeLength.Month -> RangeLengthParams.Month
is RangeLength.Year -> RangeLengthParams.Year
is RangeLength.All -> RangeLengthParams.All
is RangeLength.Custom -> RangeLengthParams.Custom(
start = range.timeStarted,
end = range.timeEnded,
)
is RangeLength.Last -> RangeLengthParams.Last(
days = days,
)
}
}
Original file line number Diff line number Diff line change
@@ -1,29 +1,17 @@
package com.example.util.simpletimetracker.core.interactor

import com.example.util.simpletimetracker.core.extension.toParams
import com.example.util.simpletimetracker.domain.interactor.PrefsInteractor
import com.example.util.simpletimetracker.domain.model.RangeLength
import com.example.util.simpletimetracker.navigation.params.screen.StatisticsDetailParams.RangeLengthParams
import com.example.util.simpletimetracker.navigation.params.screen.RangeLengthParams
import javax.inject.Inject

class GetStatisticsDetailRangeInteractor @Inject constructor(
private val prefsInteractor: PrefsInteractor,
) {

suspend fun execute(): RangeLengthParams {
return when (val rangeLength = getRangeLength()) {
is RangeLength.Day -> RangeLengthParams.Day
is RangeLength.Week -> RangeLengthParams.Week
is RangeLength.Month -> RangeLengthParams.Month
is RangeLength.Year -> RangeLengthParams.Year
is RangeLength.All -> RangeLengthParams.All
is RangeLength.Custom -> RangeLengthParams.Custom(
start = rangeLength.range.timeStarted,
end = rangeLength.range.timeEnded,
)
is RangeLength.Last -> RangeLengthParams.Last(
days = rangeLength.days,
)
}
return getRangeLength().toParams()
}

private suspend fun getRangeLength(): RangeLength {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -54,25 +54,25 @@ class RecordFilterInteractor @Inject constructor(
private val prefsInteractor: PrefsInteractor,
) {

suspend fun mapDateFilter(
fun mapDateFilter(
rangeLength: RangeLength,
rangePosition: Int,
): RecordsFilter? = withContext(Dispatchers.Default) {
): RecordsFilter {
return RecordsFilter.Date(rangeLength, rangePosition)
}

suspend fun getRange(
filter: RecordsFilter.Date,
): Range {
val firstDayOfWeek = prefsInteractor.getFirstDayOfWeek()
val startOfDayShift = prefsInteractor.getStartOfDayShift()

val range = timeMapper.getRangeStartAndEnd(
rangeLength = rangeLength,
shift = rangePosition,
return timeMapper.getRangeStartAndEnd(
rangeLength = filter.range,
shift = filter.position,
firstDayOfWeek = firstDayOfWeek,
startOfDayShift = startOfDayShift,
)

return@withContext if (range.timeStarted == 0L && range.timeEnded == 0L) {
null
} else {
RecordsFilter.Date(range)
}
}

suspend fun getByFilter(
Expand All @@ -95,7 +95,8 @@ class RecordFilterInteractor @Inject constructor(
val comments: List<String> = selectedCommentItems.getComments().map(String::lowercase)
val selectedNoComment: Boolean = selectedCommentItems.hasNoComment()
val selectedAnyComment: Boolean = selectedCommentItems.hasAnyComment()
val ranges: List<Range> = filters.getDate()?.let(::listOf).orEmpty()
val ranges: List<Range> = filters.getDate()?.let { getRange(it) }?.let(::listOf).orEmpty()
val definedRanges = ranges.filter { it.timeStarted != 0L && it.timeEnded != 0L }
val selectedTagItems: List<RecordsFilter.TagItem> = filters.getSelectedTags()
val selectedTaggedIds: List<Long> = selectedTagItems.getTaggedIds()
val selectedUntagged: Boolean = selectedTagItems.hasUntaggedItem()
Expand All @@ -111,19 +112,19 @@ class RecordFilterInteractor @Inject constructor(
// TODO by tag (tagged, untagged).
val records: List<RecordBase> = when {
filters.hasUntrackedFilter() -> {
val range = ranges.firstOrNull() ?: Range(0, 0)
val range = definedRanges.firstOrNull() ?: Range(0, 0)
val records = getAllRecords(range, runningRecords)
.map(RecordBase::toRange)
getUntrackedRecordsInteractor.get(range, records)
}
filters.hasMultitaskFilter() -> {
val range = ranges.firstOrNull() ?: Range(0, 0)
val range = definedRanges.firstOrNull() ?: Range(0, 0)
val records = getAllRecords(range, runningRecords)
getMultitaskRecordsInteractor.get(records)
}
typeIds.isNotEmpty() && ranges.isNotEmpty() -> {
typeIds.isNotEmpty() && definedRanges.isNotEmpty() -> {
val result = mutableMapOf<Long, Record>()
ranges
definedRanges
.map { interactor.getFromRangeByType(typeIds, it) }
.flatten()
.forEach { result[it.id] = it }
Expand All @@ -140,9 +141,9 @@ class RecordFilterInteractor @Inject constructor(
typeIds.isNotEmpty() -> {
interactor.getByType(typeIds)
}
ranges.isNotEmpty() -> {
definedRanges.isNotEmpty() -> {
val result = mutableMapOf<Long, Record>()
ranges
definedRanges
.map { interactor.getFromRange(it) }
.flatten()
.forEach { result[it.id] = it }
Expand All @@ -156,6 +157,7 @@ class RecordFilterInteractor @Inject constructor(
}
else -> interactor.getAll()
}.let {
// For these filter running records are added separately.
if (filters.hasUntrackedFilter() || filters.hasMultitaskFilter()) {
it
} else {
Expand All @@ -179,6 +181,8 @@ class RecordFilterInteractor @Inject constructor(

fun RecordBase.selectedByDate(): Boolean {
if (ranges.isEmpty()) return true
// Overall range.
if (ranges.any { it.timeStarted == 0L && it.timeEnded == 0L }) return true
return ranges.any { range -> timeStarted < range.timeEnded && timeEnded > range.timeStarted }
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import com.example.util.simpletimetracker.core.viewData.SelectLastDaysViewData
import com.example.util.simpletimetracker.core.viewData.SelectRangeViewData
import com.example.util.simpletimetracker.domain.extension.orZero
import com.example.util.simpletimetracker.domain.model.DayOfWeek
import com.example.util.simpletimetracker.domain.model.Range
import com.example.util.simpletimetracker.domain.model.RangeLength
import javax.inject.Inject

Expand Down Expand Up @@ -58,8 +59,8 @@ class RangeViewDataMapper @Inject constructor(
is RangeLength.Month -> timeMapper.toMonthTitle(position, startOfDayShift)
is RangeLength.Year -> timeMapper.toYearTitle(position, startOfDayShift)
is RangeLength.All -> resourceRepo.getString(R.string.range_overall)
is RangeLength.Custom -> mapToSelectRangeName()
is RangeLength.Last -> mapToSelectLastDaysName(rangeLength.days)
is RangeLength.Custom -> mapToCustomRangeTitle(rangeLength.range)
is RangeLength.Last -> mapToLastDaysTitle(rangeLength.days)
}
}

Expand Down Expand Up @@ -120,12 +121,19 @@ class RangeViewDataMapper @Inject constructor(
return resourceRepo.getString(R.string.range_custom)
}

private fun mapToCustomRangeTitle(range: Range): String {
// Time ended is the end of selected day, meaning the beginning on the next day.
return timeMapper.formatDate(range.timeStarted) +
" - " +
timeMapper.formatDate(range.timeEnded - 1)
}

private fun mapToSelectLastDays(days: Int): SelectLastDaysViewData {
val text = mapToSelectLastDaysName(days)
val text = mapToLastDaysTitle(days)
return SelectLastDaysViewData(text)
}

private fun mapToSelectLastDaysName(days: Int): String {
private fun mapToLastDaysTitle(days: Int): String {
return resourceRepo.getQuantityString(R.plurals.range_last, days, days)
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -31,9 +31,6 @@ class TimeMapper @Inject constructor(
private val timeFormatMilitaryWithSeconds by lazy { SimpleDateFormat("HH:mm:ss", locale) }

private val dateFormat by lazy { SimpleDateFormat("MMM d", locale) }
private val dateFormatWithSeconds by lazy { SimpleDateFormat("MMM d", locale) }
private val dateFormatMilitary by lazy { SimpleDateFormat("MMM d", locale) }
private val dateFormatMilitaryWithSeconds by lazy { SimpleDateFormat("MMM d", locale) }

private val dateTimeFormat by lazy { SimpleDateFormat("MMM d h:mm a", locale) }
private val dateTimeFormatWithSeconds by lazy { SimpleDateFormat("MMM d h:mm:ss a", locale) }
Expand Down Expand Up @@ -73,14 +70,8 @@ class TimeMapper @Inject constructor(
// Mar 11
fun formatDate(
time: Long,
useMilitaryTime: Boolean,
showSeconds: Boolean,
): String = synchronized(lock) {
return if (useMilitaryTime) {
if (showSeconds) dateFormatMilitaryWithSeconds else dateFormatMilitary
} else {
if (showSeconds) dateFormatWithSeconds else dateFormat
}.format(time)
return dateFormat.format(time)
}

// Mar 11 12:21
Expand Down Expand Up @@ -683,8 +674,6 @@ class TimeMapper @Inject constructor(
return DateTime(
date = formatDate(
time = time,
useMilitaryTime = useMilitaryTime,
showSeconds = showSeconds,
),
time = formatTime(
time = time,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import androidx.annotation.StringRes
import androidx.appcompat.view.ContextThemeWrapper
import androidx.core.content.ContextCompat
import androidx.core.content.res.ResourcesCompat
import com.example.util.simpletimetracker.core.R
import com.example.util.simpletimetracker.core.provider.ContextProvider
import com.example.util.simpletimetracker.feature_views.extension.pxToDp
import javax.inject.Inject
Expand Down Expand Up @@ -54,6 +55,15 @@ class ResourceRepo @Inject constructor(
}.data
}

fun getThemedAttr(attrId: Int, isDarkTheme: Boolean): Int {
val theme = if (isDarkTheme) {
R.style.AppThemeDark
} else {
R.style.AppTheme
}
return getThemedAttr(attrId = attrId, themeId = theme)
}

fun getDrawable(@DrawableRes drawableResId: Int): Drawable? {
return ResourcesCompat.getDrawable(context.resources, drawableResId, context.theme)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -64,9 +64,8 @@ fun List<RecordsFilter>.getCommentItems(): List<RecordsFilter.CommentItem> {
.flatten()
}

fun List<RecordsFilter>.getDate(): Range? {
fun List<RecordsFilter>.getDate(): RecordsFilter.Date? {
return filterIsInstance<RecordsFilter.Date>()
.map(RecordsFilter.Date::range)
.firstOrNull()
}

Expand Down Expand Up @@ -140,6 +139,10 @@ fun List<RecordsFilter.CommentItem>.getComments(): List<String> {
.map(RecordsFilter.CommentItem.Comment::text)
}

fun List<RecordsFilter>.hasDateFilter(): Boolean {
return any { it is RecordsFilter.Date }
}

fun List<RecordsFilter>.hasSelectedTagsFilter(): Boolean {
return any { it is RecordsFilter.SelectedTags }
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ sealed interface RecordsFilter {

data class Comment(val items: List<CommentItem>) : RecordsFilter

data class Date(val range: Range) : RecordsFilter
data class Date(val range: RangeLength, val position: Int) : RecordsFilter

data class SelectedTags(val items: List<TagItem>) : RecordsFilter

Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
package com.example.util.simpletimetracker.feature_base_adapter.emptySpace

import android.view.ViewGroup
import com.example.util.simpletimetracker.domain.extension.tryCast
import com.example.util.simpletimetracker.feature_base_adapter.createRecyclerBindingAdapterDelegate
import com.example.util.simpletimetracker.feature_base_adapter.emptySpace.EmptySpaceViewData.ViewDimension
import com.example.util.simpletimetracker.feature_views.extension.dpToPx
import com.google.android.flexbox.FlexboxLayoutManager
import com.example.util.simpletimetracker.feature_base_adapter.databinding.ItemEmptySpaceLayoutBinding as Binding
Expand All @@ -14,11 +16,19 @@ fun createEmptySpaceAdapterDelegate() = createRecyclerBindingAdapterDelegate<Vie
with(binding.root) {
item as ViewData

fun ViewDimension.map(): Int {
return when (this) {
is ViewDimension.WrapContent -> ViewGroup.LayoutParams.WRAP_CONTENT
is ViewDimension.MatchParent -> ViewGroup.LayoutParams.MATCH_PARENT
is ViewDimension.ExactSizeDp -> value.dpToPx()
}
}

layoutParams
.tryCast<FlexboxLayoutManager.LayoutParams>()
?.apply {
width = item.widthDp.dpToPx()
height = item.heightDp.dpToPx()
width = item.width.map()
height = item.height.map()
isWrapBefore = item.wrapBefore
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,19 @@ import com.example.util.simpletimetracker.feature_base_adapter.ViewHolderType

data class EmptySpaceViewData(
val id: Long,
val widthDp: Int = 0,
val heightDp: Int = 0,
val width: ViewDimension = ViewDimension.ExactSizeDp(0),
val height: ViewDimension = ViewDimension.ExactSizeDp(0),
val wrapBefore: Boolean = false,
) : ViewHolderType {

override fun getUniqueId(): Long = id

override fun isValidType(other: ViewHolderType): Boolean =
other is EmptySpaceViewData

sealed interface ViewDimension {
object MatchParent : ViewDimension
object WrapContent : ViewDimension
data class ExactSizeDp(val value: Int) : ViewDimension
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,7 @@ class DataEditViewModel @Inject constructor(
multitaskSelectionAvailable = false,
addRunningRecords = false,
filters = filters.map(RecordsFilter::toParams),
defaultLastDaysNumber = 7,
).let(router::navigate)
}

Expand Down
Loading

0 comments on commit 901a7e8

Please sign in to comment.