Files
psu-schedule/android/app/src/main/kotlin/ritm/schedule/widget/NextLessonWidget.kt
Zakhar Timoshenko d900e038b6 feat: add Next Lesson widget and enhance existing widgets
- Implemented a new Next Lesson widget to display the upcoming lesson details on the home screen.
- Updated Today widget to dynamically adjust the number of lessons displayed based on available space.
- Enhanced the Settings screen to allow users to manage hidden lessons more effectively.
- Introduced harmonized color palettes for better visual consistency across themes.
- Updated the timetable API to support a new range parameter for semester-based queries.
- Added tests to ensure the new semester range functionality works as expected.
- Refactored widget styling for improved appearance on devices with different Android versions.
2026-10-18 00:39:32 +03:00

86 lines
3.4 KiB
Kotlin

package ritm.schedule.widget
import android.content.Context
import androidx.compose.runtime.Composable
import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import androidx.glance.GlanceId
import androidx.glance.GlanceModifier
import androidx.glance.GlanceTheme
import androidx.glance.action.actionStartActivity
import androidx.glance.action.clickable
import androidx.glance.appwidget.GlanceAppWidget
import androidx.glance.appwidget.GlanceAppWidgetReceiver
import ritm.schedule.app
import androidx.glance.appwidget.provideContent
import androidx.glance.background
import androidx.glance.layout.Alignment
import androidx.glance.layout.Column
import androidx.glance.layout.Row
import androidx.glance.layout.Spacer
import androidx.glance.layout.fillMaxSize
import androidx.glance.layout.padding
import androidx.glance.layout.width
import androidx.glance.text.FontWeight
import androidx.glance.text.Text
import androidx.glance.text.TextStyle
import ritm.schedule.MainActivity
/** One line on the home screen: when the next lesson is, what it is and where. */
class NextLessonWidget : GlanceAppWidget() {
override suspend fun provideGlance(context: Context, id: GlanceId) {
val next = upcoming(context)
val dynamic = context.app.settings.now().dynamicColor
provideContent { WidgetTheme(dynamic) { Content(next) } }
}
@Composable
private fun Content(next: Upcoming?) {
Row(
verticalAlignment = Alignment.CenterVertically,
modifier = GlanceModifier
.fillMaxSize()
.roundedBackground(GlanceTheme.colors.widgetBackground, 28.dp)
.padding(horizontal = 16.dp, vertical = 8.dp)
.clickable(actionStartActivity<MainActivity>()),
) {
if (next == null) {
Text(
"Ближайших пар нет",
style = TextStyle(color = GlanceTheme.colors.onSurface, fontSize = 15.sp, fontWeight = FontWeight.Medium),
)
return@Row
}
Text(
next.whenLabel(),
maxLines = 1,
style = TextStyle(
color = if (next.running) GlanceTheme.colors.onPrimary else GlanceTheme.colors.onPrimaryContainer,
fontSize = 13.sp,
fontWeight = FontWeight.Bold,
),
modifier = GlanceModifier
.roundedBackground(if (next.running) GlanceTheme.colors.primary else GlanceTheme.colors.primaryContainer, 16.dp)
.padding(horizontal = 10.dp, vertical = 6.dp),
)
Spacer(GlanceModifier.width(12.dp))
Column(modifier = GlanceModifier.defaultWeight()) {
Text(
next.subject,
maxLines = 1,
style = TextStyle(color = GlanceTheme.colors.onSurface, fontSize = 15.sp, fontWeight = FontWeight.Bold),
)
if (next.rooms.isNotEmpty()) Text(
"ауд. ${next.rooms}",
maxLines = 1,
style = TextStyle(color = GlanceTheme.colors.onSurfaceVariant, fontSize = 13.sp),
)
}
}
}
}
class NextLessonWidgetReceiver : GlanceAppWidgetReceiver() {
override val glanceAppWidget: GlanceAppWidget = NextLessonWidget()
}