Fix for showing accurate next enabled alarm

This commit is contained in:
Rawlin C 2023-07-05 01:04:52 +05:30
parent d378dd4797
commit 528f0033cb
3 changed files with 90 additions and 4 deletions

View File

@ -33,6 +33,9 @@ import com.simplemobiletools.clock.receivers.HideTimerReceiver
import com.simplemobiletools.clock.services.SnoozeService
import com.simplemobiletools.commons.extensions.*
import com.simplemobiletools.commons.helpers.*
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.withContext
import java.text.SimpleDateFormat
import java.util.*
import kotlin.math.pow
@ -266,6 +269,44 @@ fun Context.getNextAlarm(): String {
return "$dayOfWeek $formatted"
}
suspend fun Context.getClosestEnabledAlarmString(): String = withContext(Dispatchers.IO) {
val enabledAlarms = dbHelper.getEnabledAlarms()
val nextAlarmList = enabledAlarms
.mapNotNull { getTimeUntilNextAlarm(it.timeInMinutes, it.days) }
if (nextAlarmList.isEmpty()) {
return@withContext ""
}
var closestAlarmTime = Int.MAX_VALUE
nextAlarmList.forEach { time ->
if (time < closestAlarmTime) {
closestAlarmTime = time
}
}
if (closestAlarmTime == Int.MAX_VALUE) {
return@withContext ""
}
val calendar = Calendar.getInstance().apply { firstDayOfWeek = Calendar.MONDAY }
calendar.add(Calendar.MINUTE, closestAlarmTime)
var dayOfWeekIndex = calendar.get(Calendar.DAY_OF_WEEK) - Calendar.MONDAY
if (dayOfWeekIndex < 0) { // Adjust for Calendar.MONDAY being 2
dayOfWeekIndex += 7
}
val dayOfWeek = resources.getStringArray(R.array.week_days_short)[dayOfWeekIndex]
val pattern = if (DateFormat.is24HourFormat(this@getClosestEnabledAlarmString)) {
"HH:mm"
} else {
"h:mm a"
}
val formattedTime = SimpleDateFormat(pattern, Locale.getDefault()).format(calendar.time)
return@withContext "$dayOfWeek $formattedTime"
}
fun Context.rescheduleEnabledAlarms() {
dbHelper.getEnabledAlarms().forEach {
if (it.days != TODAY_BIT || it.timeInMinutes > getCurrentDayMinutes()) {

View File

@ -7,6 +7,7 @@ import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import androidx.fragment.app.Fragment
import androidx.lifecycle.lifecycleScope
import com.simplemobiletools.clock.R
import com.simplemobiletools.clock.activities.SimpleActivity
import com.simplemobiletools.clock.adapters.TimeZonesAdapter
@ -20,6 +21,8 @@ import com.simplemobiletools.commons.extensions.getProperTextColor
import com.simplemobiletools.commons.extensions.updateTextColors
import kotlinx.android.synthetic.main.fragment_clock.*
import kotlinx.android.synthetic.main.fragment_clock.view.*
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.launch
import java.util.*
class ClockFragment : Fragment() {
@ -113,10 +116,12 @@ class ClockFragment : Fragment() {
fun updateAlarm() {
view.apply {
val nextAlarm = requireContext().getNextAlarm()
clock_alarm.beVisibleIf(nextAlarm.isNotEmpty())
clock_alarm.text = nextAlarm
clock_alarm.colorCompoundDrawable(requireContext().getProperTextColor())
lifecycleScope.launch {
val nextAlarm = requireContext().getClosestEnabledAlarmString()
clock_alarm.beVisibleIf(nextAlarm.isNotEmpty())
clock_alarm.text = nextAlarm
clock_alarm.colorCompoundDrawable(requireContext().getProperTextColor())
}
}
}

View File

@ -193,3 +193,43 @@ fun getAllTimeZones() = arrayListOf(
MyTimeZone(88, "GMT+13:00 Auckland", "Pacific/Auckland"),
MyTimeZone(89, "GMT+13:00 Tongatapu", "Pacific/Tongatapu")
)
fun getTimeUntilNextAlarm(alarmTimeInMinutes: Int, days: Int): Int? {
val calendar = Calendar.getInstance()
calendar.firstDayOfWeek = Calendar.MONDAY
val currentTimeInMinutes = calendar.get(Calendar.HOUR_OF_DAY) * 60 + calendar.get(Calendar.MINUTE)
val currentDayOfWeek = calendar.get(Calendar.DAY_OF_WEEK) - Calendar.MONDAY
var minTimeDifferenceInMinutes = Int.MAX_VALUE
for (i in 0..6) {
val alarmDayOfWeek = (currentDayOfWeek + i) % 7
if (isAlarmEnabledForDay(alarmDayOfWeek, days)) {
val timeDifferenceInMinutes = getTimeDifferenceInMinutes(currentTimeInMinutes, alarmTimeInMinutes, i)
if (timeDifferenceInMinutes < minTimeDifferenceInMinutes) {
minTimeDifferenceInMinutes = timeDifferenceInMinutes
}
}
}
return if (minTimeDifferenceInMinutes != Int.MAX_VALUE) {
minTimeDifferenceInMinutes
} else {
null
}
}
fun isAlarmEnabledForDay(day: Int, alarmDays: Int): Boolean {
return ((alarmDays shr day) and 1) == 1
}
fun getTimeDifferenceInMinutes(currentTimeInMinutes: Int, alarmTimeInMinutes: Int, daysUntilAlarm: Int): Int {
val minutesInADay = 24 * 60
val minutesUntilAlarm = daysUntilAlarm * minutesInADay + alarmTimeInMinutes
return if (minutesUntilAlarm > currentTimeInMinutes) {
minutesUntilAlarm - currentTimeInMinutes
} else {
minutesInADay - (currentTimeInMinutes - minutesUntilAlarm)
}
}