Skip to content

Commit

Permalink
Lesson (#20)
Browse files Browse the repository at this point in the history
* Create the UI layer of Lesson screen

* Update LessonViewState and LessonContent

* Navigate to LessonScreen from CourseScreen

* Handle back event
  • Loading branch information
nicolegeorgieva authored May 4, 2024
1 parent 936947a commit 7345228
Show file tree
Hide file tree
Showing 5 changed files with 178 additions and 2 deletions.
Original file line number Diff line number Diff line change
@@ -1,14 +1,20 @@
package ui.screen.course

import androidx.compose.runtime.*
import androidx.compose.runtime.Composable
import androidx.compose.runtime.LaunchedEffect
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.setValue
import arrow.core.identity
import data.CourseRepository
import ivy.data.source.model.CourseResponse
import ivy.model.CourseId
import ivy.model.LessonId
import kotlinx.collections.immutable.persistentListOf
import ui.ComposeViewModel
import ui.navigation.Navigation
import ui.screen.course.mapper.CourseViewStateMapper
import ui.screen.lesson.LessonScreen

class CourseViewModel(
private val courseId: CourseId,
Expand Down Expand Up @@ -47,6 +53,11 @@ class CourseViewModel(
}

private fun handleLessonClick(lesson: CourseItemViewState.Lesson) {
// TODO - navigate to lesson
navigation.navigate(
LessonScreen(
id = LessonId("4579"),
name = "Lesson 1"
)
)
}
}
29 changes: 29 additions & 0 deletions composeApp/src/commonMain/kotlin/ui/screen/lesson/LessonScreen.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
package ui.screen.lesson

import androidx.compose.runtime.Composable
import ivy.di.Di
import ivy.di.Di.register
import ivy.model.LessonId
import ui.navigation.Screen
import ui.screen.lesson.composable.LessonContent

class LessonScreen(
id: LessonId,
name: String
) : Screen() {
override val path: String = "lesson"

override fun onDi(): Di.ScreenScope.() -> Unit = {
register { LessonViewModel(Di.get()) }
}

private val viewModel: LessonViewModel by lazy { Di.get() }

@Composable
override fun Content() {
LessonContent(
viewState = viewModel.viewState(),
onEvent = viewModel::onEvent
)
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
package ui.screen.lesson

import androidx.compose.runtime.Composable
import ivy.model.ImageUrl
import ivy.model.Lesson
import ivy.model.LessonContent
import ivy.model.LessonId
import ivy.model.LessonItemId
import ivy.model.TextContentItem
import ivy.model.TextContentStyle
import ui.ComposeViewModel
import ui.navigation.Navigation

class LessonViewModel(
private val navigation: Navigation
) : ComposeViewModel<LessonViewState, LessonViewEvent> {
@Composable
override fun viewState(): LessonViewState {
return LessonViewState(
lesson = Lesson(
id = LessonId(value = "123"),
name = "Lesson 1",
tagline = "Learn programming by thinking...",
image = ImageUrl(
url = "https://cdn.pixabay.com/photo/2024/04/23/11/55/building-" +
"8714863_1280.jpg"
),
content = LessonContent(
rootItem = LessonItemId(value = "324"),
items = mapOf(
LessonItemId("4") to TextContentItem(
id = LessonItemId(value = "5"),
text = "What are ADTs - ADTs or algebraic data types are...",
style = TextContentStyle.Body,
next = null
)
)
)
)
)
}

override fun onEvent(event: LessonViewEvent) {
when (event) {
LessonViewEvent.OnBackClick -> handleBackClick()
}
}

private fun handleBackClick() {
navigation.back()
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package ui.screen.lesson

import androidx.compose.runtime.Immutable
import ivy.model.Lesson

@Immutable
data class LessonViewState(
val lesson: Lesson
)

sealed interface LessonViewEvent {
data object OnBackClick : LessonViewEvent
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
package ui.screen.lesson.composable

import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.PaddingValues
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.lazy.LazyColumn
import androidx.compose.material.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.unit.dp
import component.BackButton
import component.LearnScaffold
import component.platformHorizontalPadding
import ivy.model.ChoiceItem
import ivy.model.ImageItem
import ivy.model.LessonNavigationItem
import ivy.model.LinkItem
import ivy.model.LottieAnimationItem
import ivy.model.MysteryItem
import ivy.model.OpenQuestionItem
import ivy.model.QuestionItem
import ivy.model.TextContentItem
import ui.screen.lesson.LessonViewEvent
import ui.screen.lesson.LessonViewState

@Composable
fun LessonContent(
viewState: LessonViewState,
onEvent: (LessonViewEvent) -> Unit
) {
LearnScaffold(
backButton = BackButton(onBackClick = {
onEvent(LessonViewEvent.OnBackClick)
}),
title = viewState.lesson.name
) { contentPadding ->
val horizontalPadding = platformHorizontalPadding()
LazyColumn(
modifier = Modifier
.fillMaxSize()
.padding(contentPadding),
verticalArrangement = Arrangement.spacedBy(12.dp),
horizontalAlignment = Alignment.CenterHorizontally,
contentPadding = PaddingValues(
top = 32.dp,
bottom = 48.dp,
start = horizontalPadding,
end = horizontalPadding,
)
) {
item(key = "lesson") {
val lesson = viewState.lesson.content.items.entries.first().value
when (lesson) {
is ChoiceItem -> TODO()
is ImageItem -> TODO()
is LessonNavigationItem -> TODO()
is LinkItem -> TODO()
is LottieAnimationItem -> TODO()
is MysteryItem -> TODO()
is OpenQuestionItem -> TODO()
is QuestionItem -> TODO()
is TextContentItem -> {
Text(lesson.text)
}
}
}
}
}
}

0 comments on commit 7345228

Please sign in to comment.