Add dashboard (#1267)

This commit is contained in:
Rafał Borcz
2021-07-30 18:49:19 +02:00
committed by GitHub
parent 3278c11cce
commit 3422951e47
44 changed files with 3589 additions and 66 deletions

View File

@ -8,6 +8,7 @@ import androidx.preference.PreferenceManager
import com.chuckerteam.chucker.api.ChuckerCollector
import com.chuckerteam.chucker.api.ChuckerInterceptor
import com.chuckerteam.chucker.api.RetentionManager
import com.fredporciuncula.flow.preferences.FlowSharedPreferences
import dagger.Module
import dagger.Provides
import dagger.hilt.InstallIn
@ -18,6 +19,7 @@ import io.github.wulkanowy.data.db.SharedPrefProvider
import io.github.wulkanowy.data.repositories.PreferencesRepository
import io.github.wulkanowy.sdk.Sdk
import io.github.wulkanowy.utils.AppInfo
import kotlinx.coroutines.ExperimentalCoroutinesApi
import timber.log.Timber
import javax.inject.Singleton
@ -77,6 +79,12 @@ internal class RepositoryModule {
fun provideSharedPref(@ApplicationContext context: Context): SharedPreferences =
PreferenceManager.getDefaultSharedPreferences(context)
@OptIn(ExperimentalCoroutinesApi::class)
@Singleton
@Provides
fun provideFlowSharedPref(sharedPreferences: SharedPreferences) =
FlowSharedPreferences(sharedPreferences)
@Singleton
@Provides
fun provideStudentDao(database: AppDatabase) = database.studentDao

View File

@ -4,12 +4,13 @@ import androidx.room.Dao
import androidx.room.Query
import io.github.wulkanowy.data.db.entities.Conference
import kotlinx.coroutines.flow.Flow
import java.time.LocalDateTime
import javax.inject.Singleton
@Dao
@Singleton
interface ConferenceDao : BaseDao<Conference> {
@Query("SELECT * FROM Conferences WHERE diary_id = :diaryId AND student_id = :studentId")
fun loadAll(diaryId: Int, studentId: Int): Flow<List<Conference>>
@Query("SELECT * FROM Conferences WHERE diary_id = :diaryId AND student_id = :studentId AND date >= :startDate")
fun loadAll(diaryId: Int, studentId: Int, startDate: LocalDateTime): Flow<List<Conference>>
}

View File

@ -25,9 +25,17 @@ class AttendanceSummaryRepository @Inject constructor(
private val cacheKey = "attendance_summary"
fun getAttendanceSummary(student: Student, semester: Semester, subjectId: Int, forceRefresh: Boolean) = networkBoundResource(
fun getAttendanceSummary(
student: Student,
semester: Semester,
subjectId: Int,
forceRefresh: Boolean
) = networkBoundResource(
mutex = saveFetchResultMutex,
shouldFetch = { it.isEmpty() || forceRefresh || refreshHelper.isShouldBeRefreshed(getRefreshKey(cacheKey, semester)) },
shouldFetch = {
it.isEmpty() || forceRefresh
|| refreshHelper.isShouldBeRefreshed(getRefreshKey(cacheKey, semester))
},
query = { attendanceDb.loadAll(semester.diaryId, semester.studentId, subjectId) },
fetch = {
sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)

View File

@ -13,6 +13,9 @@ import io.github.wulkanowy.utils.networkBoundResource
import io.github.wulkanowy.utils.uniqueSubtract
import kotlinx.coroutines.flow.Flow
import kotlinx.coroutines.sync.Mutex
import java.time.Instant
import java.time.LocalDateTime
import java.time.ZoneOffset
import javax.inject.Inject
import javax.inject.Singleton
@ -31,7 +34,8 @@ class ConferenceRepository @Inject constructor(
student: Student,
semester: Semester,
forceRefresh: Boolean,
notify: Boolean = false
notify: Boolean = false,
startDate: LocalDateTime = LocalDateTime.ofInstant(Instant.EPOCH, ZoneOffset.UTC)
) = networkBoundResource(
mutex = saveFetchResultMutex,
shouldFetch = {
@ -39,15 +43,13 @@ class ConferenceRepository @Inject constructor(
|| refreshHelper.isShouldBeRefreshed(getRefreshKey(cacheKey, semester))
},
query = {
conferenceDb.loadAll(
semester.diaryId,
student.studentId
)
conferenceDb.loadAll(semester.diaryId, student.studentId, startDate)
},
fetch = {
sdk.init(student).switchDiary(semester.diaryId, semester.schoolYear)
.getConferences()
.mapToEntities(semester)
.filter { it.date >= startDate }
},
saveFetchResult = { old, new ->
val conferencesToSave = (new uniqueSubtract old).onEach {
@ -60,9 +62,12 @@ class ConferenceRepository @Inject constructor(
}
)
fun getConferenceFromDatabase(semester: Semester): Flow<List<Conference>> {
return conferenceDb.loadAll(semester.diaryId, semester.studentId)
}
fun getConferenceFromDatabase(semester: Semester): Flow<List<Conference>> =
conferenceDb.loadAll(
diaryId = semester.diaryId,
studentId = semester.studentId,
startDate = LocalDateTime.ofInstant(Instant.EPOCH, ZoneOffset.UTC)
)
suspend fun updateConference(conference: List<Conference>) = conferenceDb.updateAll(conference)
}

View File

@ -2,16 +2,24 @@ package io.github.wulkanowy.data.repositories
import android.content.Context
import android.content.SharedPreferences
import com.fredporciuncula.flow.preferences.FlowSharedPreferences
import com.fredporciuncula.flow.preferences.Preference
import dagger.hilt.android.qualifiers.ApplicationContext
import io.github.wulkanowy.R
import io.github.wulkanowy.ui.modules.dashboard.DashboardItem
import io.github.wulkanowy.ui.modules.grade.GradeAverageMode
import io.github.wulkanowy.ui.modules.grade.GradeSortingMode
import kotlinx.coroutines.ExperimentalCoroutinesApi
import kotlinx.coroutines.flow.Flow
import kotlinx.coroutines.flow.map
import javax.inject.Inject
import javax.inject.Singleton
@OptIn(ExperimentalCoroutinesApi::class)
@Singleton
class PreferencesRepository @Inject constructor(
private val sharedPref: SharedPreferences,
private val flowSharedPref: FlowSharedPreferences,
@ApplicationContext val context: Context
) {
val startMenuIndex: Int
@ -151,6 +159,36 @@ class PreferencesRepository @Inject constructor(
R.bool.pref_default_optional_arithmetic_average
)
val selectedDashboardTilesFlow: Flow<Set<DashboardItem.Tile>>
get() = selectedDashboardTilesPreference.asFlow()
.map { set ->
set.map { DashboardItem.Tile.valueOf(it) }
.plus(DashboardItem.Tile.ACCOUNT)
.toSet()
}
var selectedDashboardTiles: Set<DashboardItem.Tile>
get() = selectedDashboardTilesPreference.get()
.map { DashboardItem.Tile.valueOf(it) }
.plus(DashboardItem.Tile.ACCOUNT)
.toSet()
set(value) {
val filteredValue = value.filterNot { it == DashboardItem.Tile.ACCOUNT }
.map { it.name }
.toSet()
selectedDashboardTilesPreference.set(filteredValue)
}
private val selectedDashboardTilesPreference: Preference<Set<String>>
get() {
val defaultSet =
context.resources.getStringArray(R.array.pref_default_dashboard_tiles).toSet()
val prefKey = context.getString(R.string.pref_key_dashboard_tiles)
return flowSharedPref.getStringSet(prefKey, defaultSet)
}
private fun getString(id: Int, default: Int) = getString(context.getString(id), default)
private fun getString(id: String, default: Int) =