added skillschais screen
This commit is contained in:
parent
a35e7992b2
commit
ca36c17011
13 changed files with 264 additions and 48 deletions
2
DBTApp/.idea/deploymentTargetSelector.xml
generated
2
DBTApp/.idea/deploymentTargetSelector.xml
generated
|
|
@ -4,7 +4,7 @@
|
|||
<selectionStates>
|
||||
<SelectionState runConfigName="app">
|
||||
<option name="selectionMode" value="DROPDOWN" />
|
||||
<DropdownSelection timestamp="2025-06-05T20:16:54.801581482Z">
|
||||
<DropdownSelection timestamp="2025-06-06T15:42:28.217017051Z">
|
||||
<Target type="DEFAULT_BOOT">
|
||||
<handle>
|
||||
<DeviceId pluginId="LocalEmulator" identifier="path=/home/clara/.android/avd/Pixel_6.avd" />
|
||||
|
|
|
|||
|
|
@ -22,6 +22,7 @@ import androidx.navigation.compose.composable
|
|||
import androidx.navigation.compose.rememberNavController
|
||||
import de.cdaut.dbtapp.components.BottomNavigationBar
|
||||
import de.cdaut.dbtapp.components.FavouritesScreen
|
||||
import de.cdaut.dbtapp.components.SkillsChainsScreen
|
||||
import de.cdaut.dbtapp.components.SkillsScreen
|
||||
import de.cdaut.dbtapp.components.TrackingScreen
|
||||
import de.cdaut.dbtapp.navigation.Screens
|
||||
|
|
@ -65,7 +66,7 @@ private fun MainContent() {
|
|||
|
||||
}
|
||||
composable(Screens.Skillschains.route) {
|
||||
Text("Skillschains")
|
||||
SkillsChainsScreen()
|
||||
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -47,7 +47,7 @@ fun FavouritesScreen() {
|
|||
Modifier.verticalScroll(rememberScrollState()),
|
||||
horizontalAlignment = Alignment.CenterHorizontally
|
||||
) {
|
||||
RoundedSearchBar(onSearch = {})
|
||||
RoundedSearchBar(onSearch = {}, stringResource(R.string.label_skills_search_bar))
|
||||
SkillCategory.entries.forEach { skillCategory ->
|
||||
FavouritesCategoryCard(skillCategory)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,58 @@
|
|||
package de.cdaut.dbtapp.components
|
||||
|
||||
import androidx.compose.foundation.text.input.rememberTextFieldState
|
||||
import androidx.compose.material.icons.Icons
|
||||
import androidx.compose.material.icons.filled.Search
|
||||
import androidx.compose.material3.ExperimentalMaterial3Api
|
||||
import androidx.compose.material3.Icon
|
||||
import androidx.compose.material3.SearchBar
|
||||
import androidx.compose.material3.SearchBarDefaults
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.getValue
|
||||
import androidx.compose.runtime.mutableStateOf
|
||||
import androidx.compose.runtime.saveable.rememberSaveable
|
||||
import androidx.compose.runtime.setValue
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.tooling.preview.Preview
|
||||
import de.cdaut.dbtapp.R
|
||||
|
||||
@Preview
|
||||
@Composable
|
||||
private fun RoundedSearchBarPrev() {
|
||||
RoundedSearchBar(onSearch = {}, stringResource(R.string.label_skills_search_bar))
|
||||
}
|
||||
|
||||
@OptIn(ExperimentalMaterial3Api::class)
|
||||
@Composable
|
||||
fun RoundedSearchBar(onSearch: (String) -> Unit = {}, placeholder: String) {
|
||||
// Controls expansion state of the search bar
|
||||
var expanded by rememberSaveable { mutableStateOf(false) }
|
||||
var textFieldState = rememberTextFieldState()
|
||||
|
||||
SearchBar(
|
||||
inputField = {
|
||||
SearchBarDefaults.InputField(
|
||||
query = textFieldState.text.toString(),
|
||||
onQueryChange = { textFieldState.edit { replace(0, length, it) } },
|
||||
onSearch = {
|
||||
onSearch(textFieldState.text.toString())
|
||||
expanded = false
|
||||
},
|
||||
expanded = expanded,
|
||||
onExpandedChange = { expanded = it },
|
||||
leadingIcon = {
|
||||
Icon(
|
||||
Icons.Filled.Search,
|
||||
contentDescription = stringResource(R.string.content_desc_search_bar)
|
||||
)
|
||||
},
|
||||
placeholder = { Text(placeholder) }
|
||||
)
|
||||
},
|
||||
expanded = expanded,
|
||||
onExpandedChange = { expanded = it }
|
||||
) {
|
||||
Text("Placeholder")
|
||||
}
|
||||
}
|
||||
|
|
@ -15,25 +15,18 @@ import androidx.compose.foundation.layout.padding
|
|||
import androidx.compose.foundation.rememberScrollState
|
||||
import androidx.compose.foundation.shape.CircleShape
|
||||
import androidx.compose.foundation.shape.RoundedCornerShape
|
||||
import androidx.compose.foundation.text.input.rememberTextFieldState
|
||||
import androidx.compose.foundation.verticalScroll
|
||||
import androidx.compose.material.icons.Icons
|
||||
import androidx.compose.material.icons.filled.ArrowDropDown
|
||||
import androidx.compose.material.icons.filled.ArrowDropUp
|
||||
import androidx.compose.material.icons.filled.Search
|
||||
import androidx.compose.material.icons.filled.Star
|
||||
import androidx.compose.material.icons.outlined.StarOutline
|
||||
import androidx.compose.material3.Card
|
||||
import androidx.compose.material3.ExperimentalMaterial3Api
|
||||
import androidx.compose.material3.Icon
|
||||
import androidx.compose.material3.SearchBar
|
||||
import androidx.compose.material3.SearchBarDefaults
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.getValue
|
||||
import androidx.compose.runtime.mutableStateOf
|
||||
import androidx.compose.runtime.remember
|
||||
import androidx.compose.runtime.saveable.rememberSaveable
|
||||
import androidx.compose.runtime.setValue
|
||||
import androidx.compose.ui.Alignment
|
||||
import androidx.compose.ui.Modifier
|
||||
|
|
@ -53,7 +46,7 @@ fun SkillsScreen() {
|
|||
Modifier.verticalScroll(rememberScrollState()),
|
||||
horizontalAlignment = Alignment.CenterHorizontally
|
||||
) {
|
||||
RoundedSearchBar(onSearch = {})
|
||||
RoundedSearchBar(onSearch = {}, stringResource(R.string.label_skills_search_bar))
|
||||
SkillCategory.entries.forEach { skillCategory ->
|
||||
SkillsCategoryCard(skillCategory.skills, skillCategory.title)
|
||||
Spacer(Modifier.height(5.dp))
|
||||
|
|
@ -165,38 +158,3 @@ private fun SingleSkillCard(title: String, description: String) {
|
|||
|
||||
}
|
||||
}
|
||||
|
||||
@OptIn(ExperimentalMaterial3Api::class)
|
||||
@Preview(locale = "de")
|
||||
@Composable
|
||||
fun RoundedSearchBar(onSearch: (String) -> Unit = {}) {
|
||||
// Controls expansion state of the search bar
|
||||
var expanded by rememberSaveable { mutableStateOf(false) }
|
||||
var textFieldState = rememberTextFieldState()
|
||||
|
||||
SearchBar(
|
||||
inputField = {
|
||||
SearchBarDefaults.InputField(
|
||||
query = textFieldState.text.toString(),
|
||||
onQueryChange = { textFieldState.edit { replace(0, length, it) } },
|
||||
onSearch = {
|
||||
onSearch(textFieldState.text.toString())
|
||||
expanded = false
|
||||
},
|
||||
expanded = expanded,
|
||||
onExpandedChange = { expanded = it },
|
||||
leadingIcon = {
|
||||
Icon(
|
||||
Icons.Filled.Search,
|
||||
contentDescription = stringResource(R.string.content_desc_search_bar)
|
||||
)
|
||||
},
|
||||
placeholder = { Text(stringResource(R.string.label_search_bar)) }
|
||||
)
|
||||
},
|
||||
expanded = expanded,
|
||||
onExpandedChange = { expanded = it }
|
||||
) {
|
||||
Text("Placeholder")
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,167 @@
|
|||
package de.cdaut.dbtapp.components
|
||||
|
||||
import androidx.compose.foundation.background
|
||||
import androidx.compose.foundation.clickable
|
||||
import androidx.compose.foundation.layout.Arrangement
|
||||
import androidx.compose.foundation.layout.Column
|
||||
import androidx.compose.foundation.layout.PaddingValues
|
||||
import androidx.compose.foundation.layout.Row
|
||||
import androidx.compose.foundation.layout.Spacer
|
||||
import androidx.compose.foundation.layout.fillMaxHeight
|
||||
import androidx.compose.foundation.layout.fillMaxWidth
|
||||
import androidx.compose.foundation.layout.height
|
||||
import androidx.compose.foundation.layout.padding
|
||||
import androidx.compose.foundation.layout.size
|
||||
import androidx.compose.foundation.rememberScrollState
|
||||
import androidx.compose.foundation.shape.CircleShape
|
||||
import androidx.compose.foundation.shape.RoundedCornerShape
|
||||
import androidx.compose.foundation.verticalScroll
|
||||
import androidx.compose.material.icons.Icons
|
||||
import androidx.compose.material.icons.filled.Add
|
||||
import androidx.compose.material.icons.filled.ArrowDropDown
|
||||
import androidx.compose.material.icons.filled.ArrowDropUp
|
||||
import androidx.compose.material.icons.filled.PlayArrow
|
||||
import androidx.compose.material3.Button
|
||||
import androidx.compose.material3.Card
|
||||
import androidx.compose.material3.Icon
|
||||
import androidx.compose.material3.MaterialTheme
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.getValue
|
||||
import androidx.compose.runtime.mutableStateOf
|
||||
import androidx.compose.runtime.remember
|
||||
import androidx.compose.runtime.setValue
|
||||
import androidx.compose.ui.Alignment
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.draw.clip
|
||||
import androidx.compose.ui.graphics.Color
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.tooling.preview.Preview
|
||||
import androidx.compose.ui.unit.dp
|
||||
import de.cdaut.dbtapp.R
|
||||
import de.cdaut.dbtapp.model.Skill
|
||||
import de.cdaut.dbtapp.model.Skillschain
|
||||
import de.cdaut.dbtapp.model.Skillschain.Companion.mockSkillschains
|
||||
|
||||
@Preview
|
||||
@Composable
|
||||
fun SkillsChainsScreen() {
|
||||
Column(
|
||||
Modifier.verticalScroll(rememberScrollState()),
|
||||
horizontalAlignment = Alignment.CenterHorizontally
|
||||
) {
|
||||
RoundedSearchBar(onSearch = {}, stringResource(R.string.label_skillschains_search_bar))
|
||||
|
||||
Spacer(Modifier.height(10.dp))
|
||||
|
||||
AddSkillschainBtn()
|
||||
|
||||
mockSkillschains().forEach {
|
||||
SkillschainCard(skillschain = it)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
private fun AddSkillschainBtn(modifier: Modifier = Modifier) {
|
||||
Button(
|
||||
onClick = {
|
||||
//TODO: Add Skillschain
|
||||
},
|
||||
modifier = Modifier.fillMaxWidth(0.9f)
|
||||
) {
|
||||
Icon(
|
||||
imageVector = Icons.Filled.Add,
|
||||
contentDescription = "//TODO: Provide"
|
||||
)
|
||||
Text(stringResource(R.string.btn_add_skillschain))
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
fun SkillschainCard(modifier: Modifier = Modifier, skillschain: Skillschain) {
|
||||
|
||||
var open by remember {
|
||||
mutableStateOf(false)
|
||||
}
|
||||
|
||||
Card(
|
||||
Modifier
|
||||
.fillMaxWidth()
|
||||
.padding(10.dp)
|
||||
.background(MaterialTheme.colorScheme.primaryContainer, CircleShape)
|
||||
) {
|
||||
Column {
|
||||
Row(
|
||||
modifier = Modifier.fillMaxWidth(),
|
||||
verticalAlignment = Alignment.CenterVertically,
|
||||
horizontalArrangement = Arrangement.SpaceBetween,
|
||||
) {
|
||||
TitleText(
|
||||
modifier = Modifier.padding(10.dp),
|
||||
content = skillschain.title
|
||||
)
|
||||
Row(
|
||||
modifier = Modifier
|
||||
.padding(10.dp),
|
||||
verticalAlignment = Alignment.CenterVertically
|
||||
) {
|
||||
Button(
|
||||
modifier = Modifier
|
||||
.clip(CircleShape)
|
||||
.size(50.dp),
|
||||
contentPadding = PaddingValues(0.dp),
|
||||
shape = CircleShape,
|
||||
onClick = {
|
||||
//TODO: Start Skills Chain
|
||||
}
|
||||
) {
|
||||
Icon(
|
||||
imageVector = Icons.Filled.PlayArrow,
|
||||
contentDescription = "TODO: PROVIDE"
|
||||
)
|
||||
}
|
||||
|
||||
Icon(
|
||||
modifier = Modifier
|
||||
.padding(5.dp)
|
||||
.clickable(onClick = { open = !open }),
|
||||
imageVector = if (open) Icons.Filled.ArrowDropUp else Icons.Filled.ArrowDropDown,
|
||||
contentDescription = stringResource(R.string.desc_btn_expand)
|
||||
)
|
||||
}
|
||||
}
|
||||
if (open) {
|
||||
skillschain.skills.forEach {
|
||||
SkillCard(skill = it)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
fun SkillCard(modifier: Modifier = Modifier, skill: Skill) {
|
||||
Row(
|
||||
modifier = Modifier
|
||||
.fillMaxWidth()
|
||||
.background(Color.Transparent)
|
||||
.padding(10.dp)
|
||||
.background(Color.White, shape = RoundedCornerShape(5.dp))
|
||||
.padding(10.dp),
|
||||
horizontalArrangement = Arrangement.SpaceBetween,
|
||||
verticalAlignment = Alignment.CenterVertically
|
||||
) {
|
||||
Column(
|
||||
modifier = Modifier
|
||||
.fillMaxHeight()
|
||||
.fillMaxWidth(),
|
||||
verticalArrangement = Arrangement.SpaceBetween,
|
||||
|
||||
) {
|
||||
TitleText(skill.title)
|
||||
Spacer(modifier = Modifier.height(10.dp))
|
||||
DescriptionText(skill.description)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,28 @@
|
|||
package de.cdaut.dbtapp.model
|
||||
|
||||
import androidx.room.ColumnInfo
|
||||
import androidx.room.Entity
|
||||
import androidx.room.PrimaryKey
|
||||
import java.util.UUID
|
||||
|
||||
@Entity
|
||||
class Skillschain(
|
||||
@PrimaryKey val identifier: UUID = UUID.randomUUID(),
|
||||
@ColumnInfo(name = "name") val title: String,
|
||||
@ColumnInfo(name = "skills") val skills: List<Skill>
|
||||
) {
|
||||
companion object {
|
||||
fun mockSkillschains(): List<Skillschain> {
|
||||
return listOf(
|
||||
Skillschain(
|
||||
title = "Skillskette 1",
|
||||
skills = Skill.mockSkills()
|
||||
),
|
||||
Skillschain(
|
||||
title = "Skillskette 2",
|
||||
skills = Skill.mockSkills()
|
||||
)
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -14,6 +14,8 @@
|
|||
<string name="add_trackter">Tracker hinzufügen</string>
|
||||
<string name="view_stats">Statistiken</string>
|
||||
<string name="tracker_card_title">Tracker</string>
|
||||
<string name="label_search_bar">Skill Suchen</string>
|
||||
<string name="label_skills_search_bar">Skill Suchen</string>
|
||||
<string name="content_desc_search_bar">Suche Icon</string>
|
||||
<string name="label_skillschains_search_bar">Skillskette Suchen</string>
|
||||
<string name="btn_add_skillschain">Skillskette hinzufügen</string>
|
||||
</resources>
|
||||
|
|
@ -13,6 +13,8 @@
|
|||
<string name="add_trackter">Add Tracker</string>
|
||||
<string name="view_stats">View Statistics</string>
|
||||
<string name="tracker_card_title">Trackers</string>
|
||||
<string name="label_search_bar">Search Skill</string>
|
||||
<string name="label_skills_search_bar">Search Skill</string>
|
||||
<string name="content_desc_search_bar">Search Icon</string>
|
||||
<string name="label_skillschains_search_bar">Search Skills Chain</string>
|
||||
<string name="btn_add_skillschain">Add Skillschain</string>
|
||||
</resources>
|
||||
BIN
planning/screenshots/favourites_screen.png
Normal file
BIN
planning/screenshots/favourites_screen.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 551 KiB |
BIN
planning/screenshots/skillschains_screen.png
Normal file
BIN
planning/screenshots/skillschains_screen.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 532 KiB |
BIN
planning/screenshots/skillslist.png
Normal file
BIN
planning/screenshots/skillslist.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 549 KiB |
BIN
planning/screenshots/tracking_screen.png
Normal file
BIN
planning/screenshots/tracking_screen.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 544 KiB |
Loading…
Add table
Add a link
Reference in a new issue