forked from github/szkolny
[Events/Manual] Create custom views for dropdowns. Simplify dialog code. Fix wrong start time saving.
This commit is contained in:
parent
70c307b796
commit
611ab0f100
@ -12,8 +12,6 @@ import androidx.appcompat.app.AlertDialog
|
||||
import androidx.appcompat.app.AlertDialog.BUTTON_NEUTRAL
|
||||
import androidx.appcompat.app.AlertDialog.BUTTON_POSITIVE
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
import androidx.lifecycle.Observer
|
||||
import com.google.android.material.datepicker.MaterialDatePicker
|
||||
import com.google.android.material.dialog.MaterialAlertDialogBuilder
|
||||
import com.jaredrummler.android.colorpicker.ColorPickerDialog
|
||||
import com.jaredrummler.android.colorpicker.ColorPickerDialogListener
|
||||
@ -21,15 +19,17 @@ import kotlinx.coroutines.*
|
||||
import pl.szczodrzynski.edziennik.*
|
||||
import pl.szczodrzynski.edziennik.MainActivity.Companion.DRAWER_ITEM_AGENDA
|
||||
import pl.szczodrzynski.edziennik.data.api.szkolny.SzkolnyApi
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.*
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Event
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.EventType
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Metadata
|
||||
import pl.szczodrzynski.edziennik.data.db.full.EventFull
|
||||
import pl.szczodrzynski.edziennik.data.db.full.LessonFull
|
||||
import pl.szczodrzynski.edziennik.databinding.DialogEventManualV2Binding
|
||||
import pl.szczodrzynski.edziennik.ui.modules.views.TimeDropdown.Companion.DISPLAY_LESSONS
|
||||
import pl.szczodrzynski.edziennik.utils.Anim
|
||||
import pl.szczodrzynski.edziennik.utils.TextInputDropDown
|
||||
import pl.szczodrzynski.edziennik.utils.models.Date
|
||||
import pl.szczodrzynski.edziennik.utils.models.Time
|
||||
import pl.szczodrzynski.edziennik.utils.models.Week
|
||||
import kotlin.coroutines.CoroutineContext
|
||||
|
||||
class EventManualDialog(
|
||||
@ -56,7 +56,6 @@ class EventManualDialog(
|
||||
private lateinit var b: DialogEventManualV2Binding
|
||||
private lateinit var dialog: AlertDialog
|
||||
|
||||
private lateinit var event: Event
|
||||
private var customColor: Int? = null
|
||||
private val editingShared = editingEvent?.sharedBy != null
|
||||
private val editingOwn = editingEvent?.sharedBy == "self"
|
||||
@ -104,12 +103,6 @@ class EventManualDialog(
|
||||
show()
|
||||
}
|
||||
|
||||
event = editingEvent?.clone() ?: Event().also { event ->
|
||||
event.profileId = profileId
|
||||
defaultType?.let {
|
||||
event.type = it
|
||||
}
|
||||
}
|
||||
b.shareSwitch.isChecked = editingShared
|
||||
b.shareSwitch.isEnabled = !editingShared || (editingShared && editingOwn)
|
||||
|
||||
@ -144,41 +137,85 @@ class EventManualDialog(
|
||||
else -> R.string.dialog_event_manual_share_first_notice
|
||||
}
|
||||
|
||||
b.shareDetails.setText(text, event.sharedByName ?: "")
|
||||
b.shareDetails.setText(text, editingEvent?.sharedByName ?: "")
|
||||
}
|
||||
|
||||
private fun loadLists() { launch {
|
||||
with (b.dateDropdown) {
|
||||
db = app.db
|
||||
profileId = App.profileId
|
||||
showWeekDays = false
|
||||
showDays = true
|
||||
showOtherDate = true
|
||||
defaultLesson?.let {
|
||||
nextLessonSubjectId = it.displaySubjectId
|
||||
nextLessonSubjectName = it.displaySubjectName
|
||||
nextLessonTeamId = it.displayTeamId
|
||||
}
|
||||
loadItems()
|
||||
selectDefault(editingEvent?.eventDate)
|
||||
selectDefault(defaultLesson?.displayDate ?: defaultDate)
|
||||
onDateSelected = { date, lesson ->
|
||||
b.timeDropdown.deselect()
|
||||
b.timeDropdown.lessonsDate = date
|
||||
this@EventManualDialog.launch {
|
||||
b.timeDropdown.loadItems()
|
||||
lesson?.displayStartTime?.let { b.timeDropdown.selectTime(it) }
|
||||
lesson?.displaySubjectId?.let { b.subjectDropdown.selectSubject(it) } ?: b.subjectDropdown.deselect()
|
||||
lesson?.displayTeacherId?.let { b.teacherDropdown.selectTeacher(it) } ?: b.teacherDropdown.deselect()
|
||||
lesson?.displayTeamId?.let { b.teamDropdown.selectTeam(it) } ?: b.teamDropdown.selectTeamClass()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
with (b.timeDropdown) {
|
||||
db = app.db
|
||||
profileId = App.profileId
|
||||
showAllDay = true
|
||||
showCustomTime = true
|
||||
lessonsDate = b.dateDropdown.getSelected() as? Date ?: Date.getToday()
|
||||
displayMode = DISPLAY_LESSONS
|
||||
loadItems()
|
||||
selectDefault(editingEvent?.startTime)
|
||||
selectDefault(defaultLesson?.displayStartTime ?: defaultTime)
|
||||
onLessonSelected = { lesson ->
|
||||
lesson.displaySubjectId?.let { b.subjectDropdown.selectSubject(it) } ?: b.subjectDropdown.deselect()
|
||||
lesson.displayTeacherId?.let { b.teacherDropdown.selectTeacher(it) } ?: b.teacherDropdown.deselect()
|
||||
lesson.displayTeamId?.let { b.teamDropdown.selectTeam(it) } ?: b.teamDropdown.selectTeamClass()
|
||||
}
|
||||
}
|
||||
|
||||
with (b.teamDropdown) {
|
||||
db = app.db
|
||||
profileId = App.profileId
|
||||
showNoTeam = true
|
||||
loadItems()
|
||||
selectTeamClass()
|
||||
selectDefault(editingEvent?.teamId)
|
||||
selectDefault(defaultLesson?.displayTeamId)
|
||||
}
|
||||
|
||||
with (b.subjectDropdown) {
|
||||
db = app.db
|
||||
profileId = App.profileId
|
||||
showNoSubject = true
|
||||
showCustomSubject = false
|
||||
loadItems()
|
||||
selectDefault(editingEvent?.subjectId)
|
||||
selectDefault(defaultLesson?.displaySubjectId)
|
||||
}
|
||||
|
||||
with (b.teacherDropdown) {
|
||||
db = app.db
|
||||
profileId = App.profileId
|
||||
showNoTeacher = true
|
||||
loadItems()
|
||||
selectDefault(editingEvent?.teacherId)
|
||||
selectDefault(defaultLesson?.displayTeacherId)
|
||||
}
|
||||
|
||||
|
||||
val deferred = async(Dispatchers.Default) {
|
||||
// get the team list
|
||||
val teams = app.db.teamDao().getAllNow(profileId)
|
||||
b.teamDropdown.clear()
|
||||
b.teamDropdown += TextInputDropDown.Item(
|
||||
-1,
|
||||
activity.getString(R.string.dialog_event_manual_no_team),
|
||||
""
|
||||
)
|
||||
b.teamDropdown += teams.map { TextInputDropDown.Item(it.id, it.name, tag = it) }
|
||||
|
||||
// get the subject list
|
||||
val subjects = app.db.subjectDao().getAllNow(profileId)
|
||||
b.subjectDropdown.clear()
|
||||
b.subjectDropdown += TextInputDropDown.Item(
|
||||
-1,
|
||||
activity.getString(R.string.dialog_event_manual_no_subject),
|
||||
""
|
||||
)
|
||||
b.subjectDropdown += subjects.map { TextInputDropDown.Item(it.id, it.longName, tag = it) }
|
||||
|
||||
// get the teacher list
|
||||
val teachers = app.db.teacherDao().getAllNow(profileId)
|
||||
b.teacherDropdown.clear()
|
||||
b.teacherDropdown += TextInputDropDown.Item(
|
||||
-1,
|
||||
activity.getString(R.string.dialog_event_manual_no_teacher),
|
||||
""
|
||||
)
|
||||
b.teacherDropdown += teachers.map { TextInputDropDown.Item(it.id, it.fullName, tag = it) }
|
||||
|
||||
// get the event type list
|
||||
val eventTypes = app.db.eventTypeDao().getAllNow(profileId)
|
||||
b.typeDropdown.clear()
|
||||
@ -186,13 +223,10 @@ class EventManualDialog(
|
||||
}
|
||||
deferred.await()
|
||||
|
||||
b.teamDropdown.isEnabled = true
|
||||
b.subjectDropdown.isEnabled = true
|
||||
b.teacherDropdown.isEnabled = true
|
||||
b.typeDropdown.isEnabled = true
|
||||
|
||||
defaultType?.let {
|
||||
b.typeDropdown.select(it.toLong())
|
||||
b.typeDropdown.select(it)
|
||||
}
|
||||
|
||||
b.typeDropdown.selected?.let { item ->
|
||||
@ -201,9 +235,6 @@ class EventManualDialog(
|
||||
|
||||
// copy IDs from event being edited
|
||||
editingEvent?.let {
|
||||
b.teamDropdown.select(it.teamId)
|
||||
b.subjectDropdown.select(it.subjectId)
|
||||
b.teacherDropdown.select(it.teacherId)
|
||||
b.topic.setText(it.topic)
|
||||
b.typeDropdown.select(it.type.toLong())?.let { item ->
|
||||
customColor = (item.tag as EventType).color
|
||||
@ -215,8 +246,6 @@ class EventManualDialog(
|
||||
// copy IDs from the LessonFull
|
||||
defaultLesson?.let {
|
||||
b.teamDropdown.select(it.displayTeamId)
|
||||
b.subjectDropdown.select(it.displaySubjectId)
|
||||
b.teacherDropdown.select(it.displayTeacherId)
|
||||
}
|
||||
|
||||
b.typeDropdown.setOnChangeListener {
|
||||
@ -244,278 +273,8 @@ class EventManualDialog(
|
||||
})
|
||||
colorPickerDialog.show(activity.fragmentManager, "color-picker-dialog")
|
||||
}
|
||||
|
||||
loadDates()
|
||||
}}
|
||||
|
||||
private fun loadDates() { launch {
|
||||
val date = Date.getToday()
|
||||
val today = date.value
|
||||
var weekDay = date.weekDay
|
||||
|
||||
val deferred = async(Dispatchers.Default) {
|
||||
val dates = mutableListOf<TextInputDropDown.Item>()
|
||||
// item choosing the next lesson of specific subject
|
||||
b.subjectDropdown.selected?.let {
|
||||
if (it.tag is Subject) {
|
||||
dates += TextInputDropDown.Item(
|
||||
-it.id,
|
||||
activity.getString(R.string.dialog_event_manual_date_next_lesson, it.tag.longName)
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
// TODAY
|
||||
dates += TextInputDropDown.Item(
|
||||
date.value.toLong(),
|
||||
activity.getString(R.string.dialog_event_manual_date_today, date.formattedString),
|
||||
tag = date.clone()
|
||||
)
|
||||
|
||||
// TOMORROW
|
||||
if (weekDay < 4) {
|
||||
date.stepForward(0, 0, 1)
|
||||
weekDay++
|
||||
dates += TextInputDropDown.Item(
|
||||
date.value.toLong(),
|
||||
activity.getString(R.string.dialog_event_manual_date_tomorrow, date.formattedString),
|
||||
tag = date.clone()
|
||||
)
|
||||
}
|
||||
// REMAINING SCHOOL DAYS OF THE CURRENT WEEK
|
||||
while (weekDay < 4) {
|
||||
date.stepForward(0, 0, 1) // step one day forward
|
||||
weekDay++
|
||||
dates += TextInputDropDown.Item(
|
||||
date.value.toLong(),
|
||||
activity.getString(R.string.dialog_event_manual_date_this_week, Week.getFullDayName(weekDay), date.formattedString),
|
||||
tag = date.clone()
|
||||
)
|
||||
}
|
||||
// go to next week Monday
|
||||
date.stepForward(0, 0, -weekDay + 7)
|
||||
weekDay = 0
|
||||
// ALL SCHOOL DAYS OF THE NEXT WEEK
|
||||
while (weekDay < 4) {
|
||||
dates += TextInputDropDown.Item(
|
||||
date.value.toLong(),
|
||||
activity.getString(R.string.dialog_event_manual_date_next_week, Week.getFullDayName(weekDay), date.formattedString),
|
||||
tag = date.clone()
|
||||
)
|
||||
date.stepForward(0, 0, 1) // step one day forward
|
||||
weekDay++
|
||||
}
|
||||
dates += TextInputDropDown.Item(
|
||||
-1L,
|
||||
activity.getString(R.string.dialog_event_manual_date_other)
|
||||
)
|
||||
dates
|
||||
}
|
||||
|
||||
val dates = deferred.await()
|
||||
b.dateDropdown.clear().append(dates)
|
||||
|
||||
defaultDate?.let {
|
||||
event.eventDate = it
|
||||
if (b.dateDropdown.select(it) == null)
|
||||
b.dateDropdown.select(TextInputDropDown.Item(
|
||||
it.value.toLong(),
|
||||
it.formattedString,
|
||||
tag = it
|
||||
))
|
||||
}
|
||||
|
||||
editingEvent?.eventDate?.let {
|
||||
b.dateDropdown.select(TextInputDropDown.Item(
|
||||
it.value.toLong(),
|
||||
it.formattedString,
|
||||
tag = it
|
||||
))
|
||||
}
|
||||
|
||||
defaultLesson?.displayDate?.let {
|
||||
b.dateDropdown.select(TextInputDropDown.Item(
|
||||
it.value.toLong(),
|
||||
it.formattedString,
|
||||
tag = it
|
||||
))
|
||||
}
|
||||
|
||||
if (b.dateDropdown.selected == null) {
|
||||
b.dateDropdown.select(today.toLong())
|
||||
}
|
||||
|
||||
b.dateDropdown.isEnabled = true
|
||||
|
||||
b.dateDropdown.setOnChangeListener { item ->
|
||||
when {
|
||||
// next lesson with specified subject
|
||||
item.id < -1 -> {
|
||||
val teamId = defaultLesson?.teamId ?: -1
|
||||
val selectedLessonDate = defaultLesson?.date ?: Date.getToday()
|
||||
|
||||
when (teamId) {
|
||||
-1L -> app.db.timetableDao().getNextWithSubject(profileId, selectedLessonDate, -item.id)
|
||||
else -> app.db.timetableDao().getNextWithSubjectAndTeam(profileId, selectedLessonDate, -item.id, teamId)
|
||||
}.observeOnce(activity, Observer {
|
||||
val lessonDate = it?.displayDate ?: return@Observer
|
||||
b.dateDropdown.select(TextInputDropDown.Item(
|
||||
lessonDate.value.toLong(),
|
||||
lessonDate.formattedString,
|
||||
tag = lessonDate
|
||||
))
|
||||
b.teamDropdown.select(it.displayTeamId)
|
||||
b.subjectDropdown.select(it.displaySubjectId)
|
||||
b.teacherDropdown.select(it.displayTeacherId)
|
||||
defaultLoaded = false
|
||||
loadHours(it.displayStartTime)
|
||||
})
|
||||
return@setOnChangeListener false
|
||||
}
|
||||
// custom date
|
||||
item.id == -1L -> {
|
||||
MaterialDatePicker.Builder
|
||||
.datePicker()
|
||||
.setSelection((b.dateDropdown.selectedId?.let { Date.fromValue(it.toInt()) }
|
||||
?: Date.getToday()).inMillis)
|
||||
.build()
|
||||
.apply {
|
||||
addOnPositiveButtonClickListener {
|
||||
val dateSelected = Date.fromMillis(it)
|
||||
b.dateDropdown.select(TextInputDropDown.Item(
|
||||
dateSelected.value.toLong(),
|
||||
dateSelected.formattedString,
|
||||
tag = dateSelected
|
||||
))
|
||||
loadHours()
|
||||
}
|
||||
show(this@EventManualDialog.activity.supportFragmentManager, "MaterialDatePicker")
|
||||
}
|
||||
|
||||
return@setOnChangeListener false
|
||||
}
|
||||
// a specific date
|
||||
else -> {
|
||||
b.dateDropdown.select(item)
|
||||
loadHours()
|
||||
}
|
||||
}
|
||||
return@setOnChangeListener true
|
||||
}
|
||||
|
||||
loadHours()
|
||||
}}
|
||||
|
||||
private fun loadHours(defaultHour: Time? = null) {
|
||||
b.timeDropdown.isEnabled = false
|
||||
// get the selected date
|
||||
val date = b.dateDropdown.selectedId?.let { Date.fromValue(it.toInt()) } ?: return
|
||||
// get all lessons for selected date
|
||||
app.db.timetableDao().getForDate(profileId, date).observeOnce(activity, Observer { lessons ->
|
||||
val hours = mutableListOf<TextInputDropDown.Item>()
|
||||
// add All day time choice
|
||||
hours += TextInputDropDown.Item(
|
||||
0L,
|
||||
activity.getString(R.string.dialog_event_manual_all_day)
|
||||
)
|
||||
lessons.forEach { lesson ->
|
||||
if (lesson.type == Lesson.TYPE_NO_LESSONS) {
|
||||
// indicate there are no lessons this day
|
||||
hours += TextInputDropDown.Item(
|
||||
-2L,
|
||||
activity.getString(R.string.dialog_event_manual_no_lessons)
|
||||
)
|
||||
return@forEach
|
||||
}
|
||||
// create the lesson caption
|
||||
val text = listOfNotEmpty(
|
||||
lesson.displayStartTime?.stringHM ?: "",
|
||||
lesson.displaySubjectName?.let {
|
||||
when {
|
||||
lesson.type == Lesson.TYPE_CANCELLED
|
||||
|| lesson.type == Lesson.TYPE_SHIFTED_SOURCE -> it.asStrikethroughSpannable()
|
||||
lesson.type != Lesson.TYPE_NORMAL -> it.asItalicSpannable()
|
||||
else -> it
|
||||
}
|
||||
} ?: ""
|
||||
)
|
||||
// add an item with LessonFull as the tag
|
||||
hours += TextInputDropDown.Item(
|
||||
lesson.displayStartTime?.value?.toLong() ?: -1,
|
||||
text.concat(" "),
|
||||
tag = lesson
|
||||
)
|
||||
}
|
||||
b.timeDropdown.clear().append(hours)
|
||||
|
||||
if (defaultLoaded) {
|
||||
b.timeDropdown.deselect()
|
||||
// select the TEAM_CLASS if possible
|
||||
b.teamDropdown.items.singleOrNull {
|
||||
it.tag is Team && it.tag.type == Team.TYPE_CLASS
|
||||
}?.let {
|
||||
b.teamDropdown.select(it)
|
||||
} ?: b.teamDropdown.deselect()
|
||||
|
||||
// clear subject, teacher selection
|
||||
b.subjectDropdown.deselect()
|
||||
b.teacherDropdown.deselect()
|
||||
}
|
||||
else {
|
||||
val setTime: (Time) -> Unit = {
|
||||
event.startTime = it
|
||||
if (b.timeDropdown.select(it) == null)
|
||||
b.timeDropdown.select(TextInputDropDown.Item(
|
||||
it.value.toLong(),
|
||||
it.stringHM,
|
||||
tag = it
|
||||
))
|
||||
}
|
||||
defaultTime?.let(setTime)
|
||||
editingEvent?.startTime?.let(setTime)
|
||||
defaultLesson?.displayStartTime?.let(setTime)
|
||||
defaultHour?.let(setTime)
|
||||
}
|
||||
defaultLoaded = true
|
||||
b.timeDropdown.isEnabled = true
|
||||
|
||||
// attach a listener to time dropdown
|
||||
b.timeDropdown.setOnChangeListener { item ->
|
||||
when (item.id) {
|
||||
// no lessons this day
|
||||
-2L -> {
|
||||
b.timeDropdown.deselect()
|
||||
return@setOnChangeListener false
|
||||
}
|
||||
|
||||
// custom start hour
|
||||
-1L -> return@setOnChangeListener false
|
||||
|
||||
// selected a specific lesson
|
||||
else -> {
|
||||
if (item.tag is LessonFull) {
|
||||
// update team, subject, teacher dropdowns,
|
||||
// using the LessonFull from item tag
|
||||
b.teamDropdown.deselect()
|
||||
b.subjectDropdown.deselect()
|
||||
b.teacherDropdown.deselect()
|
||||
item.tag.displayTeamId?.let {
|
||||
b.teamDropdown.select(it)
|
||||
}
|
||||
item.tag.displaySubjectId?.let {
|
||||
b.subjectDropdown.select(it)
|
||||
}
|
||||
item.tag.displayTeacherId?.let {
|
||||
b.teacherDropdown.select(it)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return@setOnChangeListener true
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
private fun showRemoveEventDialog() {
|
||||
val shareNotice = when {
|
||||
editingShared && editingOwn -> "\n\n"+activity.getString(R.string.dialog_event_manual_remove_shared_self)
|
||||
@ -541,22 +300,29 @@ class EventManualDialog(
|
||||
}
|
||||
|
||||
private fun saveEvent() {
|
||||
val date = b.dateDropdown.selected?.tag.instanceOfOrNull<Date>()
|
||||
val startTime = b.timeDropdown.selected?.tag.instanceOfOrNull<Time>()
|
||||
val teamId = b.teamDropdown.selected?.id
|
||||
val date = b.dateDropdown.getSelected() as? Date
|
||||
val startTimePair = b.timeDropdown.getSelected() as? Pair<*, *>
|
||||
val startTime = startTimePair?.first as? Time
|
||||
val teamId = b.teamDropdown.getSelected() as? Long
|
||||
val type = b.typeDropdown.selected?.id
|
||||
val topic = b.topic.text?.toString()
|
||||
val subjectId = b.subjectDropdown.selected?.id
|
||||
val teacherId = b.teacherDropdown.selected?.id
|
||||
val subjectId = b.subjectDropdown.getSelected() as? Long
|
||||
val teacherId = b.teacherDropdown.getSelected() as? Long
|
||||
|
||||
val share = b.shareSwitch.isChecked
|
||||
|
||||
b.dateDropdown.error = null
|
||||
b.teamDropdown.error = null
|
||||
b.typeDropdown.error = null
|
||||
b.topic.error = null
|
||||
|
||||
var isError = false
|
||||
|
||||
if (date == null) {
|
||||
b.dateDropdown.error = app.getString(R.string.dialog_event_manual_date_choose)
|
||||
isError = true
|
||||
}
|
||||
|
||||
if (share && teamId == null) {
|
||||
b.teamDropdown.error = app.getString(R.string.dialog_event_manual_team_choose)
|
||||
isError = true
|
||||
|
@ -0,0 +1,240 @@
|
||||
/*
|
||||
* Copyright (c) Kuba Szczodrzyński 2020-2-23.
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.modules.views
|
||||
|
||||
import android.content.Context
|
||||
import android.content.ContextWrapper
|
||||
import android.util.AttributeSet
|
||||
import android.widget.Toast
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
import androidx.lifecycle.Observer
|
||||
import com.google.android.material.datepicker.MaterialDatePicker
|
||||
import kotlinx.coroutines.Dispatchers
|
||||
import kotlinx.coroutines.withContext
|
||||
import pl.szczodrzynski.edziennik.R
|
||||
import pl.szczodrzynski.edziennik.data.db.AppDb
|
||||
import pl.szczodrzynski.edziennik.data.db.full.LessonFull
|
||||
import pl.szczodrzynski.edziennik.observeOnce
|
||||
import pl.szczodrzynski.edziennik.utils.TextInputDropDown
|
||||
import pl.szczodrzynski.edziennik.utils.models.Date
|
||||
import pl.szczodrzynski.edziennik.utils.models.Week
|
||||
|
||||
class DateDropdown : TextInputDropDown {
|
||||
constructor(context: Context) : super(context)
|
||||
constructor(context: Context, attrs: AttributeSet) : super(context, attrs)
|
||||
constructor(context: Context, attrs: AttributeSet, defStyleAttr: Int) : super(context, attrs, defStyleAttr)
|
||||
|
||||
private val activity: AppCompatActivity?
|
||||
get() {
|
||||
var context: Context? = context ?: return null
|
||||
if (context is AppCompatActivity) return context
|
||||
while (context is ContextWrapper) {
|
||||
if (context is AppCompatActivity)
|
||||
return context
|
||||
context = context.baseContext
|
||||
}
|
||||
return null
|
||||
}
|
||||
|
||||
lateinit var db: AppDb
|
||||
var profileId: Int = 0
|
||||
var showWeekDays = false
|
||||
var showDays = true
|
||||
var showOtherDate = true
|
||||
var nextLessonSubjectId: Long? = null
|
||||
var nextLessonSubjectName: String? = null
|
||||
var nextLessonTeamId: Long? = null
|
||||
var onDateSelected: ((date: Date, lesson: LessonFull?) -> Unit)? = null
|
||||
var onWeekDaySelected: ((weekDay: Int) -> Unit)? = null
|
||||
|
||||
override fun create(context: Context) {
|
||||
super.create(context)
|
||||
isEnabled = false
|
||||
}
|
||||
|
||||
suspend fun loadItems() {
|
||||
val date = Date.getToday()
|
||||
val today = date.value
|
||||
var weekDay = date.weekDay
|
||||
|
||||
val dates = withContext(Dispatchers.Default) {
|
||||
val dates = mutableListOf<Item>()
|
||||
|
||||
nextLessonSubjectId?.let {
|
||||
// item choosing the next lesson of specific subject - relative to selected date
|
||||
dates += Item(
|
||||
-it,
|
||||
context.getString(R.string.dialog_event_manual_date_next_lesson, nextLessonSubjectName),
|
||||
tag = nextLessonSubjectName
|
||||
)
|
||||
}
|
||||
|
||||
if (showWeekDays) {
|
||||
for (i in Week.MONDAY..Week.SUNDAY) {
|
||||
dates += Item(
|
||||
i.toLong(),
|
||||
Week.getFullDayName(i),
|
||||
tag = i
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
if (showDays) {
|
||||
// TODAY
|
||||
dates += Item(
|
||||
date.value.toLong(),
|
||||
context.getString(R.string.dialog_event_manual_date_today, date.formattedString),
|
||||
tag = date.clone()
|
||||
)
|
||||
|
||||
// TOMORROW
|
||||
if (weekDay < 4) {
|
||||
date.stepForward(0, 0, 1)
|
||||
weekDay++
|
||||
dates += Item(
|
||||
date.value.toLong(),
|
||||
context.getString(R.string.dialog_event_manual_date_tomorrow, date.formattedString),
|
||||
tag = date.clone()
|
||||
)
|
||||
}
|
||||
// REMAINING SCHOOL DAYS OF THE CURRENT WEEK
|
||||
while (weekDay < 4) {
|
||||
date.stepForward(0, 0, 1) // step one day forward
|
||||
weekDay++
|
||||
dates += Item(
|
||||
date.value.toLong(),
|
||||
context.getString(R.string.dialog_event_manual_date_this_week, Week.getFullDayName(weekDay), date.formattedString),
|
||||
tag = date.clone()
|
||||
)
|
||||
}
|
||||
// go to next week Monday
|
||||
date.stepForward(0, 0, -weekDay + 7)
|
||||
weekDay = 0
|
||||
// ALL SCHOOL DAYS OF THE NEXT WEEK
|
||||
while (weekDay < 4) {
|
||||
dates += Item(
|
||||
date.value.toLong(),
|
||||
context.getString(R.string.dialog_event_manual_date_next_week, Week.getFullDayName(weekDay), date.formattedString),
|
||||
tag = date.clone()
|
||||
)
|
||||
date.stepForward(0, 0, 1) // step one day forward
|
||||
weekDay++
|
||||
}
|
||||
}
|
||||
|
||||
if (showOtherDate) {
|
||||
dates += Item(
|
||||
-1L,
|
||||
context.getString(R.string.dialog_event_manual_date_other),
|
||||
tag = -1L
|
||||
)
|
||||
}
|
||||
dates
|
||||
}
|
||||
|
||||
clear().append(dates)
|
||||
isEnabled = true
|
||||
|
||||
setOnChangeListener { item ->
|
||||
when (item.tag) {
|
||||
-1L -> {
|
||||
pickerDialog()
|
||||
false
|
||||
}
|
||||
is Date -> {
|
||||
onDateSelected?.invoke(item.tag, null)
|
||||
true
|
||||
}
|
||||
is Int -> {
|
||||
onWeekDaySelected?.invoke(item.tag)
|
||||
true
|
||||
}
|
||||
is String -> {
|
||||
/* next lesson of subject */
|
||||
activity ?: return@setOnChangeListener false
|
||||
val subjectId = -item.id
|
||||
val startDate = getSelected() as? Date ?: Date.getToday()
|
||||
when (nextLessonTeamId) {
|
||||
null -> db.timetableDao().getNextWithSubject(profileId, startDate, subjectId)
|
||||
else -> db.timetableDao().getNextWithSubjectAndTeam(profileId, startDate, subjectId, nextLessonTeamId ?: -1)
|
||||
}.observeOnce(activity!!, Observer {
|
||||
if (it == null) {
|
||||
Toast.makeText(context, R.string.dropdown_date_no_more_lessons, Toast.LENGTH_LONG).show()
|
||||
return@Observer
|
||||
}
|
||||
val lessonDate = it.displayDate ?: return@Observer
|
||||
selectDate(lessonDate)
|
||||
onDateSelected?.invoke(lessonDate, it)
|
||||
})
|
||||
false
|
||||
}
|
||||
else -> false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun pickerDialog() {
|
||||
MaterialDatePicker.Builder
|
||||
.datePicker()
|
||||
.setSelection(
|
||||
if (selected?.tag is Date)
|
||||
(selected?.tag as Date).inMillis
|
||||
else
|
||||
Date.getToday().inMillis
|
||||
)
|
||||
.build()
|
||||
.apply {
|
||||
addOnPositiveButtonClickListener {
|
||||
val dateSelected = Date.fromMillis(it)
|
||||
selectDate(dateSelected)
|
||||
}
|
||||
this@DateDropdown.activity ?: return@apply
|
||||
show(this@DateDropdown.activity!!.supportFragmentManager, "MaterialDatePicker")
|
||||
}
|
||||
}
|
||||
|
||||
fun selectDate(date: Date) {
|
||||
if (select(date) == null)
|
||||
select(Item(
|
||||
date.value.toLong(),
|
||||
date.formattedString,
|
||||
tag = date
|
||||
))
|
||||
}
|
||||
fun selectWeekDay(weekDay: Int) {
|
||||
if (select(tag = weekDay) == null)
|
||||
select(Item(
|
||||
weekDay.toLong(),
|
||||
Week.getFullDayName(weekDay),
|
||||
tag = weekDay
|
||||
))
|
||||
}
|
||||
|
||||
fun selectDefault(date: Date?) {
|
||||
if (date == null || selected != null)
|
||||
return
|
||||
selectDate(date)
|
||||
}
|
||||
fun selectDefault(weekDay: Int?) {
|
||||
if (weekDay == null || selected != null)
|
||||
return
|
||||
selectWeekDay(weekDay)
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the currently selected date.
|
||||
* ### Returns:
|
||||
* - null if no valid date is selected
|
||||
* - [Date] - the selected date, if [showDays] or [showOtherDate] == true
|
||||
* - [Int] - the selected week day, if [showWeekDays] == true
|
||||
*/
|
||||
fun getSelected(): Any? {
|
||||
return when (val tag = selected?.tag) {
|
||||
is Date -> tag
|
||||
is Int -> tag
|
||||
else -> null
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,153 @@
|
||||
/*
|
||||
* Copyright (c) Kuba Szczodrzyński 2020-2-23.
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.modules.views
|
||||
|
||||
import android.content.Context
|
||||
import android.content.ContextWrapper
|
||||
import android.text.InputType
|
||||
import android.util.AttributeSet
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
import com.afollestad.materialdialogs.MaterialDialog
|
||||
import kotlinx.coroutines.Dispatchers
|
||||
import kotlinx.coroutines.withContext
|
||||
import pl.szczodrzynski.edziennik.R
|
||||
import pl.szczodrzynski.edziennik.crc16
|
||||
import pl.szczodrzynski.edziennik.data.db.AppDb
|
||||
import pl.szczodrzynski.edziennik.utils.TextInputDropDown
|
||||
|
||||
class SubjectDropdown : TextInputDropDown {
|
||||
constructor(context: Context) : super(context)
|
||||
constructor(context: Context, attrs: AttributeSet) : super(context, attrs)
|
||||
constructor(context: Context, attrs: AttributeSet, defStyleAttr: Int) : super(context, attrs, defStyleAttr)
|
||||
|
||||
private val activity: AppCompatActivity?
|
||||
get() {
|
||||
var context: Context? = context ?: return null
|
||||
if (context is AppCompatActivity) return context
|
||||
while (context is ContextWrapper) {
|
||||
if (context is AppCompatActivity)
|
||||
return context
|
||||
context = context.baseContext
|
||||
}
|
||||
return null
|
||||
}
|
||||
|
||||
lateinit var db: AppDb
|
||||
var profileId: Int = 0
|
||||
var showNoSubject = true
|
||||
var showCustomSubject = false
|
||||
var customSubjectName = ""
|
||||
var onSubjectSelected: ((subjectId: Long?) -> Unit)? = null
|
||||
var onCustomSubjectSelected: ((subjectName: String) -> Unit)? = null
|
||||
|
||||
override fun create(context: Context) {
|
||||
super.create(context)
|
||||
isEnabled = false
|
||||
}
|
||||
|
||||
suspend fun loadItems() {
|
||||
val subjects = withContext(Dispatchers.Default) {
|
||||
val list = mutableListOf<Item>()
|
||||
|
||||
if (showNoSubject) {
|
||||
list += Item(
|
||||
-1L,
|
||||
context.getString(R.string.dialog_event_manual_no_subject),
|
||||
tag = -1L
|
||||
)
|
||||
}
|
||||
|
||||
if (showCustomSubject) {
|
||||
list += Item(
|
||||
-2L,
|
||||
context.getString(R.string.dropdown_subject_custom),
|
||||
tag = -2L
|
||||
)
|
||||
}
|
||||
|
||||
val subjects = db.subjectDao().getAllNow(profileId)
|
||||
|
||||
list += subjects.map { Item(
|
||||
it.id,
|
||||
it.longName,
|
||||
tag = it.id
|
||||
) }
|
||||
|
||||
list
|
||||
}
|
||||
|
||||
clear().append(subjects)
|
||||
isEnabled = true
|
||||
|
||||
setOnChangeListener {
|
||||
when (it.tag) {
|
||||
-2L -> {
|
||||
// custom subject
|
||||
customNameDialog()
|
||||
false
|
||||
}
|
||||
-1L -> {
|
||||
// no subject
|
||||
onSubjectSelected?.invoke(null)
|
||||
true
|
||||
}
|
||||
is Long -> {
|
||||
// selected a subject
|
||||
onSubjectSelected?.invoke(it.tag)
|
||||
true
|
||||
}
|
||||
else -> false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun customNameDialog() {
|
||||
activity ?: return
|
||||
MaterialDialog.Builder(activity!!)
|
||||
.title("Własny przedmiot")
|
||||
.inputType(InputType.TYPE_CLASS_TEXT or InputType.TYPE_TEXT_VARIATION_SHORT_MESSAGE)
|
||||
.input("Nazwa", "") { _: MaterialDialog?, input: CharSequence ->
|
||||
customSubjectName = input.toString()
|
||||
select(Item(
|
||||
-1L * customSubjectName.crc16(),
|
||||
customSubjectName,
|
||||
tag = customSubjectName
|
||||
))
|
||||
onCustomSubjectSelected?.invoke(customSubjectName)
|
||||
}
|
||||
.show()
|
||||
}
|
||||
|
||||
fun selectSubject(subjectId: Long) {
|
||||
if (select(subjectId) == null)
|
||||
select(Item(
|
||||
subjectId,
|
||||
"nieznany przedmiot ($subjectId)",
|
||||
tag = subjectId
|
||||
))
|
||||
}
|
||||
|
||||
fun selectDefault(subjectId: Long?) {
|
||||
if (subjectId == null || selected != null)
|
||||
return
|
||||
selectSubject(subjectId)
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the currently selected subject.
|
||||
* ### Returns:
|
||||
* - null if no valid subject is selected
|
||||
* - [Long] - the selected subject's ID
|
||||
* - [String] - a custom subject name entered, if [showCustomSubject] == true
|
||||
*/
|
||||
fun getSelected(): Any? {
|
||||
return when (selected?.tag) {
|
||||
-1L -> null
|
||||
is Long -> selected?.tag as Long
|
||||
is String -> selected?.tag as String
|
||||
else -> null
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,115 @@
|
||||
/*
|
||||
* Copyright (c) Kuba Szczodrzyński 2020-2-23.
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.modules.views
|
||||
|
||||
import android.content.Context
|
||||
import android.content.ContextWrapper
|
||||
import android.util.AttributeSet
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
import kotlinx.coroutines.Dispatchers
|
||||
import kotlinx.coroutines.withContext
|
||||
import pl.szczodrzynski.edziennik.R
|
||||
import pl.szczodrzynski.edziennik.data.db.AppDb
|
||||
import pl.szczodrzynski.edziennik.utils.TextInputDropDown
|
||||
|
||||
class TeacherDropdown : TextInputDropDown {
|
||||
constructor(context: Context) : super(context)
|
||||
constructor(context: Context, attrs: AttributeSet) : super(context, attrs)
|
||||
constructor(context: Context, attrs: AttributeSet, defStyleAttr: Int) : super(context, attrs, defStyleAttr)
|
||||
|
||||
private val activity: AppCompatActivity?
|
||||
get() {
|
||||
var context: Context? = context ?: return null
|
||||
if (context is AppCompatActivity) return context
|
||||
while (context is ContextWrapper) {
|
||||
if (context is AppCompatActivity)
|
||||
return context
|
||||
context = context.baseContext
|
||||
}
|
||||
return null
|
||||
}
|
||||
|
||||
lateinit var db: AppDb
|
||||
var profileId: Int = 0
|
||||
var showNoTeacher = true
|
||||
var onTeacherSelected: ((teacherId: Long?) -> Unit)? = null
|
||||
|
||||
override fun create(context: Context) {
|
||||
super.create(context)
|
||||
isEnabled = false
|
||||
}
|
||||
|
||||
suspend fun loadItems() {
|
||||
val teachers = withContext(Dispatchers.Default) {
|
||||
val list = mutableListOf<Item>()
|
||||
|
||||
if (showNoTeacher) {
|
||||
list += Item(
|
||||
-1L,
|
||||
context.getString(R.string.dialog_event_manual_no_teacher),
|
||||
tag = -1L
|
||||
)
|
||||
}
|
||||
|
||||
val teachers = db.teacherDao().getAllNow(profileId)
|
||||
|
||||
list += teachers.map { Item(
|
||||
it.id,
|
||||
it.fullName,
|
||||
tag = it.id
|
||||
) }
|
||||
|
||||
list
|
||||
}
|
||||
|
||||
clear().append(teachers)
|
||||
isEnabled = true
|
||||
|
||||
setOnChangeListener {
|
||||
when (it.tag) {
|
||||
-1L -> {
|
||||
// no teacher
|
||||
onTeacherSelected?.invoke(null)
|
||||
true
|
||||
}
|
||||
is Long -> {
|
||||
// selected a teacher
|
||||
onTeacherSelected?.invoke(it.tag)
|
||||
true
|
||||
}
|
||||
else -> false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun selectTeacher(teacherId: Long) {
|
||||
if (select(teacherId) == null)
|
||||
select(Item(
|
||||
teacherId,
|
||||
"nieznany nauczyciel ($teacherId)",
|
||||
tag = teacherId
|
||||
))
|
||||
}
|
||||
|
||||
fun selectDefault(teacherId: Long?) {
|
||||
if (teacherId == null || selected != null)
|
||||
return
|
||||
selectTeacher(teacherId)
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the currently selected teacher.
|
||||
* ### Returns:
|
||||
* - null if no valid teacher is selected
|
||||
* - [Long] - the selected teacher's ID
|
||||
*/
|
||||
fun getSelected(): Long? {
|
||||
return when (selected?.tag) {
|
||||
-1L -> null
|
||||
is Long -> selected?.tag as Long
|
||||
else -> null
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,122 @@
|
||||
/*
|
||||
* Copyright (c) Kuba Szczodrzyński 2020-3-7.
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.modules.views
|
||||
|
||||
import android.content.Context
|
||||
import android.content.ContextWrapper
|
||||
import android.util.AttributeSet
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
import kotlinx.coroutines.Dispatchers
|
||||
import kotlinx.coroutines.withContext
|
||||
import pl.szczodrzynski.edziennik.R
|
||||
import pl.szczodrzynski.edziennik.data.db.AppDb
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Team
|
||||
import pl.szczodrzynski.edziennik.utils.TextInputDropDown
|
||||
|
||||
class TeamDropdown : TextInputDropDown {
|
||||
constructor(context: Context) : super(context)
|
||||
constructor(context: Context, attrs: AttributeSet) : super(context, attrs)
|
||||
constructor(context: Context, attrs: AttributeSet, defStyleAttr: Int) : super(context, attrs, defStyleAttr)
|
||||
|
||||
private val activity: AppCompatActivity?
|
||||
get() {
|
||||
var context: Context? = context ?: return null
|
||||
if (context is AppCompatActivity) return context
|
||||
while (context is ContextWrapper) {
|
||||
if (context is AppCompatActivity)
|
||||
return context
|
||||
context = context.baseContext
|
||||
}
|
||||
return null
|
||||
}
|
||||
|
||||
lateinit var db: AppDb
|
||||
var profileId: Int = 0
|
||||
var showNoTeam = true
|
||||
var onTeamSelected: ((teamId: Long?) -> Unit)? = null
|
||||
|
||||
override fun create(context: Context) {
|
||||
super.create(context)
|
||||
isEnabled = false
|
||||
}
|
||||
|
||||
suspend fun loadItems() {
|
||||
val teams = withContext(Dispatchers.Default) {
|
||||
val list = mutableListOf<Item>()
|
||||
|
||||
if (showNoTeam) {
|
||||
list += Item(
|
||||
-1L,
|
||||
context.getString(R.string.dialog_event_manual_no_team),
|
||||
tag = -1L
|
||||
)
|
||||
}
|
||||
|
||||
val teams = db.teamDao().getAllNow(profileId)
|
||||
|
||||
list += teams.map { Item(
|
||||
it.id,
|
||||
it.name,
|
||||
tag = it.id
|
||||
) }
|
||||
|
||||
list
|
||||
}
|
||||
|
||||
clear().append(teams)
|
||||
isEnabled = true
|
||||
|
||||
setOnChangeListener {
|
||||
when (it.tag) {
|
||||
-1L -> {
|
||||
// no team
|
||||
onTeamSelected?.invoke(null)
|
||||
true
|
||||
}
|
||||
is Long -> {
|
||||
// selected a team
|
||||
onTeamSelected?.invoke(it.tag)
|
||||
true
|
||||
}
|
||||
else -> false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun selectTeam(teamId: Long) {
|
||||
if (select(teamId) == null)
|
||||
select(Item(
|
||||
teamId,
|
||||
"nieznana grupa ($teamId)",
|
||||
tag = teamId
|
||||
))
|
||||
}
|
||||
|
||||
fun selectDefault(teamId: Long?) {
|
||||
if (teamId == null || selected != null)
|
||||
return
|
||||
selectTeam(teamId)
|
||||
}
|
||||
|
||||
fun selectTeamClass() {
|
||||
select(items.singleOrNull {
|
||||
it.tag is Team && it.tag.type == Team.TYPE_CLASS
|
||||
})
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the currently selected team.
|
||||
* ### Returns:
|
||||
* - null if no valid team is selected
|
||||
* - [Long] - the team's ID
|
||||
*/
|
||||
fun getSelected(): Any? {
|
||||
return when (selected?.tag) {
|
||||
-1L -> null
|
||||
is Long -> selected?.tag as Long
|
||||
else -> null
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,214 @@
|
||||
/*
|
||||
* Copyright (c) Kuba Szczodrzyński 2020-2-23.
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.modules.views
|
||||
|
||||
import android.content.Context
|
||||
import android.content.ContextWrapper
|
||||
import android.util.AttributeSet
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
import kotlinx.coroutines.Dispatchers
|
||||
import kotlinx.coroutines.withContext
|
||||
import pl.szczodrzynski.edziennik.*
|
||||
import pl.szczodrzynski.edziennik.data.db.AppDb
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Lesson
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.LessonRange
|
||||
import pl.szczodrzynski.edziennik.data.db.full.LessonFull
|
||||
import pl.szczodrzynski.edziennik.utils.TextInputDropDown
|
||||
import pl.szczodrzynski.edziennik.utils.models.Date
|
||||
import pl.szczodrzynski.edziennik.utils.models.Time
|
||||
|
||||
class TimeDropdown : TextInputDropDown {
|
||||
companion object {
|
||||
const val DISPLAY_LESSON_RANGES = 0
|
||||
const val DISPLAY_LESSONS = 1
|
||||
}
|
||||
|
||||
constructor(context: Context) : super(context)
|
||||
constructor(context: Context, attrs: AttributeSet) : super(context, attrs)
|
||||
constructor(context: Context, attrs: AttributeSet, defStyleAttr: Int) : super(context, attrs, defStyleAttr)
|
||||
|
||||
private val activity: AppCompatActivity?
|
||||
get() {
|
||||
var context: Context? = context ?: return null
|
||||
if (context is AppCompatActivity) return context
|
||||
while (context is ContextWrapper) {
|
||||
if (context is AppCompatActivity)
|
||||
return context
|
||||
context = context.baseContext
|
||||
}
|
||||
return null
|
||||
}
|
||||
|
||||
lateinit var db: AppDb
|
||||
var profileId: Int = 0
|
||||
var showAllDay = false
|
||||
var showCustomTime = true
|
||||
var displayMode = DISPLAY_LESSON_RANGES
|
||||
var lessonsDate: Date? = null
|
||||
var onTimeSelected: ((startTime: Time?, endTime: Time?, lessonNumber: Int?) -> Unit)? = null
|
||||
var onLessonSelected: ((lesson: LessonFull) -> Unit)? = null
|
||||
|
||||
override fun create(context: Context) {
|
||||
super.create(context)
|
||||
isEnabled = false
|
||||
}
|
||||
|
||||
suspend fun loadItems() {
|
||||
val hours = withContext(Dispatchers.Default) {
|
||||
val hours = mutableListOf<Item>()
|
||||
|
||||
if (showAllDay) {
|
||||
hours += Item(
|
||||
0L,
|
||||
context.getString(R.string.dialog_event_manual_all_day),
|
||||
tag = 0L
|
||||
)
|
||||
}
|
||||
|
||||
if (showCustomTime) {
|
||||
hours += Item(
|
||||
-1,
|
||||
context.getString(R.string.dialog_event_manual_custom_time),
|
||||
tag = -1L
|
||||
)
|
||||
}
|
||||
|
||||
if (displayMode == DISPLAY_LESSON_RANGES) {
|
||||
val lessonRanges = db.lessonRangeDao().getAllNow(profileId)
|
||||
|
||||
hours += lessonRanges.map { Item(
|
||||
it.startTime.value.toLong(),
|
||||
context.getString(R.string.timetable_manual_dialog_time_format, it.startTime.stringHM, it.lessonNumber),
|
||||
tag = it
|
||||
) }
|
||||
}
|
||||
else if (displayMode == DISPLAY_LESSONS && lessonsDate != null) {
|
||||
val lessons = db.timetableDao().getForDateNow(profileId, lessonsDate!!)
|
||||
|
||||
hours += lessons.map { lesson ->
|
||||
if (lesson.type == Lesson.TYPE_NO_LESSONS) {
|
||||
// indicate there are no lessons this day
|
||||
return@map Item(
|
||||
-2L,
|
||||
context.getString(R.string.dialog_event_manual_no_lessons),
|
||||
tag = -2L
|
||||
)
|
||||
}
|
||||
// create the lesson caption
|
||||
val text = listOfNotEmpty(
|
||||
lesson.displayStartTime?.stringHM ?: "",
|
||||
if (lesson.displaySubjectName != null) "-" else "",
|
||||
lesson.displaySubjectName?.let {
|
||||
when {
|
||||
lesson.type == Lesson.TYPE_CANCELLED
|
||||
|| lesson.type == Lesson.TYPE_SHIFTED_SOURCE -> it.asStrikethroughSpannable()
|
||||
lesson.type != Lesson.TYPE_NORMAL -> it.asItalicSpannable()
|
||||
else -> it
|
||||
}
|
||||
} ?: ""
|
||||
)
|
||||
// add an item with LessonFull as the tag
|
||||
return@map Item(
|
||||
lesson.displayStartTime?.value?.toLong() ?: -1,
|
||||
text.concat(" "),
|
||||
tag = lesson
|
||||
)
|
||||
}
|
||||
}
|
||||
hours
|
||||
}
|
||||
|
||||
clear().append(hours)
|
||||
isEnabled = true
|
||||
|
||||
setOnChangeListener {
|
||||
when (it.tag) {
|
||||
-2L -> {
|
||||
// no lessons this day
|
||||
deselect()
|
||||
false
|
||||
}
|
||||
-1L -> {
|
||||
// custom start hour
|
||||
pickerDialog()
|
||||
false
|
||||
}
|
||||
0L -> {
|
||||
// selected all day
|
||||
onTimeSelected?.invoke(null, null, null)
|
||||
true
|
||||
}
|
||||
is LessonFull -> {
|
||||
// selected a specific lesson
|
||||
onLessonSelected?.invoke(it.tag)
|
||||
true
|
||||
}
|
||||
is LessonRange -> {
|
||||
// selected a lesson range
|
||||
onTimeSelected?.invoke(it.tag.startTime, it.tag.endTime, it.tag.lessonNumber)
|
||||
true
|
||||
}
|
||||
is Time -> {
|
||||
// selected a time
|
||||
onTimeSelected?.invoke(it.tag, null, null)
|
||||
true
|
||||
}
|
||||
else -> false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun pickerDialog() {
|
||||
/*MaterialDatePicker.Builder
|
||||
.datePicker()
|
||||
.setSelection((selectedId?.let { Date.fromValue(it.toInt()) }
|
||||
?: Date.getToday()).inMillis)
|
||||
.build()
|
||||
.apply {
|
||||
addOnPositiveButtonClickListener {
|
||||
val dateSelected = Date.fromMillis(it)
|
||||
selectDate(dateSelected)
|
||||
}
|
||||
this@DateDropdown.activity ?: return@apply
|
||||
show(this@DateDropdown.activity!!.supportFragmentManager, "MaterialDatePicker")
|
||||
}*/
|
||||
}
|
||||
|
||||
fun selectTime(time: Time) {
|
||||
if (select(time.value.toLong()) == null)
|
||||
select(Item(
|
||||
time.value.toLong(),
|
||||
time.stringHM,
|
||||
tag = time
|
||||
))
|
||||
}
|
||||
|
||||
fun selectDefault(time: Time?) {
|
||||
if (time == null || selected != null)
|
||||
return
|
||||
selectTime(time)
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the currently selected time.
|
||||
* ### Returns:
|
||||
* - null if no valid time is selected
|
||||
* - a [Pair] of [Time] and [Time]? - the selected time object, if [displayMode] == [DISPLAY_LESSONS] or [showCustomTime]
|
||||
* - [LessonRange] - the selected lesson range object, if [displayMode] == [DISPLAY_LESSON_RANGES]
|
||||
*/
|
||||
fun getSelected(): Any? {
|
||||
return when (val tag = selected?.tag) {
|
||||
0L -> null
|
||||
is LessonFull ->
|
||||
if (tag.displayStartTime != null)
|
||||
tag.displayStartTime!! to tag.displayEndTime
|
||||
else
|
||||
null
|
||||
is LessonRange -> tag
|
||||
is Time -> tag to null
|
||||
else -> null
|
||||
}
|
||||
}
|
||||
}
|
@ -7,7 +7,7 @@ import androidx.core.graphics.drawable.DrawableCompat
|
||||
import com.google.android.material.textfield.TextInputEditText
|
||||
import pl.szczodrzynski.edziennik.R
|
||||
|
||||
class TextInputDropDown : TextInputEditText {
|
||||
open class TextInputDropDown : TextInputEditText {
|
||||
constructor(context: Context) : super(context) {
|
||||
create(context)
|
||||
}
|
||||
@ -31,7 +31,7 @@ class TextInputDropDown : TextInputEditText {
|
||||
setText(selected?.displayText ?: selected?.text)
|
||||
}
|
||||
|
||||
fun create(context: Context) {
|
||||
open fun create(context: Context) {
|
||||
val drawable = context.resources.getDrawable(R.drawable.dropdown_arrow)
|
||||
val wrappedDrawable = DrawableCompat.wrap(drawable)
|
||||
DrawableCompat.setTint(wrappedDrawable, Themes.getPrimaryTextColor(context))
|
||||
|
@ -24,7 +24,7 @@
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:hint="@string/dialog_event_manual_date">
|
||||
<pl.szczodrzynski.edziennik.utils.TextInputDropDown
|
||||
<pl.szczodrzynski.edziennik.ui.modules.views.DateDropdown
|
||||
android:id="@+id/dateDropdown"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
@ -38,7 +38,7 @@
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="8dp"
|
||||
android:hint="@string/dialog_event_manual_time">
|
||||
<pl.szczodrzynski.edziennik.utils.TextInputDropDown
|
||||
<pl.szczodrzynski.edziennik.ui.modules.views.TimeDropdown
|
||||
android:id="@+id/timeDropdown"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
@ -53,7 +53,7 @@
|
||||
android:layout_marginTop="8dp"
|
||||
android:hint="@string/dialog_event_manual_team">
|
||||
|
||||
<pl.szczodrzynski.edziennik.utils.TextInputDropDown
|
||||
<pl.szczodrzynski.edziennik.ui.modules.views.TeamDropdown
|
||||
android:id="@+id/teamDropdown"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
@ -158,7 +158,7 @@
|
||||
android:layout_marginTop="8dp"
|
||||
android:hint="@string/dialog_event_manual_subject">
|
||||
|
||||
<pl.szczodrzynski.edziennik.utils.TextInputDropDown
|
||||
<pl.szczodrzynski.edziennik.ui.modules.views.SubjectDropdown
|
||||
android:id="@+id/subjectDropdown"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
@ -173,7 +173,7 @@
|
||||
android:layout_marginTop="8dp"
|
||||
android:hint="@string/dialog_event_manual_teacher">
|
||||
|
||||
<pl.szczodrzynski.edziennik.utils.TextInputDropDown
|
||||
<pl.szczodrzynski.edziennik.ui.modules.views.TeacherDropdown
|
||||
android:id="@+id/teacherDropdown"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
|
@ -294,6 +294,12 @@
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
<View
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="1dp"
|
||||
android:layout_marginTop="8dp"
|
||||
android:background="@drawable/divider"/>
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/eventsNoData"
|
||||
android:layout_width="match_parent"
|
||||
@ -331,7 +337,6 @@
|
||||
android:id="@+id/eventsView"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="8dp"
|
||||
android:clipToPadding="false"
|
||||
tools:visibility="visible"
|
||||
tools:listitem="@layout/event_list_item" />
|
||||
|
@ -1233,4 +1233,8 @@
|
||||
<string name="grades_stats_help_text">Ocena przewidywana z danego przedmiotu jest obliczana na podstawie aktualnej średniej ważonej.\n\nOcena jest liczbą całkowitą, jaką wystawił by nauczyciel bazując na średniej. Liczba zaokrąglona jest w górę jeśli część po przecinku przekroczy ,75.\nPrzykładowo: średnie 3,75 jak również 4,74 dają w wyniku ocenę dobrą (4).\n\nŚrednia przewidywana ze wszystkich przedmiotów obejmuje obliczone w ten sposób oceny końcowe.</string>
|
||||
<string name="grades_stats_custom_value_notice">Została ustawiona własna wartość plusa/minusa. Jeśli uważasz, że średnia się nie zgadza, kliknij Konfiguruj.</string>
|
||||
<string name="configure">Konfiguruj</string>
|
||||
<string name="menu_timetable_manual">Edytor planu lekcji</string>
|
||||
<string name="dropdown_subject_custom">Własny przedmiot</string>
|
||||
<string name="dialog_event_manual_date_choose">Wybierz datę</string>
|
||||
<string name="dropdown_date_no_more_lessons">Nie ma więcej lekcji tego przedmiotu. Pobierz plan lekcji i spróbuj ponownie.</string>
|
||||
</resources>
|
||||
|
Loading…
Reference in New Issue
Block a user