Add flat value management for attack skill and spell.
This commit is contained in:
parent
8e9529d4d0
commit
2cc1a0ea70
13 changed files with 262 additions and 119 deletions
|
|
@ -843,7 +843,7 @@ class DiceThrowUseCase @Inject constructor(
|
||||||
)
|
)
|
||||||
|
|
||||||
// fetch and build a list of additional level effect.
|
// fetch and build a list of additional level effect.
|
||||||
val levelBonus = if (spell?.level != null) {
|
val levelBonus = if (spell?.level?.dice != null) {
|
||||||
((spell.spell.level + 1)..level).map {
|
((spell.spell.level + 1)..level).map {
|
||||||
val localRoll = roll(
|
val localRoll = roll(
|
||||||
amount = spell.level.dice.count,
|
amount = spell.level.dice.count,
|
||||||
|
|
|
||||||
|
|
@ -3,7 +3,7 @@ package com.pixelized.rplexicon.data.model.roll
|
||||||
import com.pixelized.rplexicon.data.model.Property
|
import com.pixelized.rplexicon.data.model.Property
|
||||||
|
|
||||||
class Throw(
|
class Throw(
|
||||||
val dice: Dice,
|
val dice: Dice?,
|
||||||
val flat: Flat?,
|
val flat: Flat?,
|
||||||
val modifier: List<Property>,
|
val modifier: List<Property>,
|
||||||
)
|
)
|
||||||
|
|
@ -10,14 +10,11 @@ class ThrowParser @Inject constructor(
|
||||||
) {
|
) {
|
||||||
fun parse(value: String?): Throw? {
|
fun parse(value: String?): Throw? {
|
||||||
if (value != null) {
|
if (value != null) {
|
||||||
val dice = diceParser.parse(value = value).firstOrNull()
|
return Throw(
|
||||||
if (dice != null) {
|
dice = diceParser.parse(value = value).firstOrNull(),
|
||||||
return Throw(
|
flat = flatValueParser.parse(value = value),
|
||||||
dice = dice,
|
modifier = modifierParser.parse(value = value),
|
||||||
flat = flatValueParser.parse(value = value),
|
)
|
||||||
modifier = modifierParser.parse(value = value),
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return null
|
return null
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -32,6 +32,7 @@ import com.pixelized.rplexicon.R
|
||||||
import com.pixelized.rplexicon.data.model.Attack
|
import com.pixelized.rplexicon.data.model.Attack
|
||||||
import com.pixelized.rplexicon.ui.composable.AsyncImage
|
import com.pixelized.rplexicon.ui.composable.AsyncImage
|
||||||
import com.pixelized.rplexicon.ui.screens.character.composable.common.DiceButton
|
import com.pixelized.rplexicon.ui.screens.character.composable.common.DiceButton
|
||||||
|
import com.pixelized.rplexicon.ui.screens.character.composable.common.FlatValue
|
||||||
import com.pixelized.rplexicon.ui.theme.LexiconTheme
|
import com.pixelized.rplexicon.ui.theme.LexiconTheme
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.uri
|
import com.pixelized.rplexicon.utilitary.extentions.uri
|
||||||
|
|
||||||
|
|
@ -42,14 +43,22 @@ data class AttackUio(
|
||||||
val name: String,
|
val name: String,
|
||||||
@StringRes val type: Int,
|
@StringRes val type: Int,
|
||||||
val range: String?,
|
val range: String?,
|
||||||
val hit: Dice?,
|
val hit: Action?,
|
||||||
val damage: Dice?,
|
val damage: Action?,
|
||||||
) {
|
) {
|
||||||
@Stable
|
@Stable
|
||||||
class Dice(
|
sealed class Action {
|
||||||
@DrawableRes val icon: Int,
|
@Stable
|
||||||
val label: String,
|
class Dice(
|
||||||
)
|
@DrawableRes val icon: Int,
|
||||||
|
val label: String,
|
||||||
|
) : Action()
|
||||||
|
|
||||||
|
@Stable
|
||||||
|
class Flat(
|
||||||
|
val label: String,
|
||||||
|
) : Action()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Composable
|
@Composable
|
||||||
|
|
@ -106,19 +115,31 @@ fun Attack(
|
||||||
Row(
|
Row(
|
||||||
horizontalArrangement = Arrangement.spacedBy(space = 4.dp),
|
horizontalArrangement = Arrangement.spacedBy(space = 4.dp),
|
||||||
) {
|
) {
|
||||||
weapon.hit?.let { dice ->
|
weapon.hit?.let { action ->
|
||||||
DiceButton(
|
when (action) {
|
||||||
icon = dice.icon,
|
is AttackUio.Action.Dice -> DiceButton(
|
||||||
text = dice.label,
|
icon = action.icon,
|
||||||
onClick = { weapon.name.let(onHit) }
|
text = action.label,
|
||||||
)
|
onClick = { weapon.name.let(onHit) }
|
||||||
|
)
|
||||||
|
|
||||||
|
is AttackUio.Action.Flat -> FlatValue(
|
||||||
|
text = action.label,
|
||||||
|
)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
weapon.damage?.let { dice ->
|
weapon.damage?.let { action ->
|
||||||
DiceButton(
|
when (action) {
|
||||||
icon = dice.icon,
|
is AttackUio.Action.Dice -> DiceButton(
|
||||||
text = dice.label,
|
icon = action.icon,
|
||||||
onClick = { weapon.name.let(onDamage) }
|
text = action.label,
|
||||||
)
|
onClick = { weapon.name.let(onDamage) }
|
||||||
|
)
|
||||||
|
|
||||||
|
is AttackUio.Action.Flat -> FlatValue(
|
||||||
|
text = action.label,
|
||||||
|
)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -147,19 +168,19 @@ private class WeaponPreviewProvider : PreviewParameterProvider<AttackUio> {
|
||||||
override val values: Sequence<AttackUio> = sequenceOf(
|
override val values: Sequence<AttackUio> = sequenceOf(
|
||||||
AttackUio(
|
AttackUio(
|
||||||
icon = R.drawable.ic_crossed_swords_24.uri.toUri(),
|
icon = R.drawable.ic_crossed_swords_24.uri.toUri(),
|
||||||
name = "Dagger",
|
name = "Sans arme",
|
||||||
type = R.string.attack_type_melee,
|
type = R.string.attack_type_melee,
|
||||||
range = "5 ft reach",
|
range = "5 ft reach",
|
||||||
hit = AttackUio.Dice(icon = R.drawable.ic_d20_24, label = "1d20"),
|
hit = AttackUio.Action.Dice(icon = R.drawable.ic_d20_24, label = "1d20"),
|
||||||
damage = AttackUio.Dice(icon = R.drawable.ic_d8_24, label = "1d8"),
|
damage = AttackUio.Action.Flat(label = "1"),
|
||||||
),
|
),
|
||||||
AttackUio(
|
AttackUio(
|
||||||
icon = R.drawable.ic_pocket_bow_24.uri.toUri(),
|
icon = R.drawable.ic_pocket_bow_24.uri.toUri(),
|
||||||
name = "Long bow",
|
name = "Long bow",
|
||||||
type = R.string.attack_type_range,
|
type = R.string.attack_type_range,
|
||||||
range = "30 ft reach",
|
range = "30 ft reach",
|
||||||
hit = AttackUio.Dice(icon = R.drawable.ic_d20_24, label = "1d20+5"),
|
hit = AttackUio.Action.Dice(icon = R.drawable.ic_d20_24, label = "1d20+5"),
|
||||||
damage = AttackUio.Dice(icon = R.drawable.ic_d8_24, label = "1d8+3"),
|
damage = AttackUio.Action.Dice(icon = R.drawable.ic_d8_24, label = "1d8+3"),
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
@ -33,6 +33,7 @@ import com.pixelized.rplexicon.R
|
||||||
import com.pixelized.rplexicon.ui.composable.AsyncImage
|
import com.pixelized.rplexicon.ui.composable.AsyncImage
|
||||||
import com.pixelized.rplexicon.ui.screens.character.composable.common.CounterButton
|
import com.pixelized.rplexicon.ui.screens.character.composable.common.CounterButton
|
||||||
import com.pixelized.rplexicon.ui.screens.character.composable.common.DiceButton
|
import com.pixelized.rplexicon.ui.screens.character.composable.common.DiceButton
|
||||||
|
import com.pixelized.rplexicon.ui.screens.character.composable.common.FlatValue
|
||||||
import com.pixelized.rplexicon.ui.theme.LexiconTheme
|
import com.pixelized.rplexicon.ui.theme.LexiconTheme
|
||||||
|
|
||||||
@Stable
|
@Stable
|
||||||
|
|
@ -42,15 +43,24 @@ data class SkillItemUio(
|
||||||
val translate: String?,
|
val translate: String?,
|
||||||
val rest: String?,
|
val rest: String?,
|
||||||
val cost: String?,
|
val cost: String?,
|
||||||
val effect: Dice?,
|
val effect: Action?,
|
||||||
val value: Int?,
|
val value: Int?,
|
||||||
val max: Int?,
|
val max: Int?,
|
||||||
val haveDetail: Boolean,
|
val haveDetail: Boolean,
|
||||||
) {
|
) {
|
||||||
class Dice(
|
@Stable
|
||||||
@DrawableRes val icon: Int,
|
sealed class Action {
|
||||||
val label: String,
|
@Stable
|
||||||
)
|
class Dice(
|
||||||
|
@DrawableRes val icon: Int,
|
||||||
|
val label: String,
|
||||||
|
) : Action()
|
||||||
|
|
||||||
|
@Stable
|
||||||
|
class Flat(
|
||||||
|
val label: String,
|
||||||
|
) : Action()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Composable
|
@Composable
|
||||||
|
|
@ -131,11 +141,17 @@ fun SkillItem(
|
||||||
}
|
}
|
||||||
|
|
||||||
skill.effect?.let { effect ->
|
skill.effect?.let { effect ->
|
||||||
DiceButton(
|
when (effect) {
|
||||||
icon = effect.icon,
|
is SkillItemUio.Action.Dice -> DiceButton(
|
||||||
text = effect.label,
|
icon = effect.icon,
|
||||||
onClick = { onThrow(skill) },
|
text = effect.label,
|
||||||
)
|
onClick = { onThrow(skill) },
|
||||||
|
)
|
||||||
|
|
||||||
|
is SkillItemUio.Action.Flat -> FlatValue(
|
||||||
|
text = effect.label,
|
||||||
|
)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
skill.max?.let {
|
skill.max?.let {
|
||||||
|
|
@ -193,7 +209,7 @@ private class CounterItemPreviewProvider : PreviewParameterProvider<SkillItemUio
|
||||||
translate = "Mantle of Inspiration",
|
translate = "Mantle of Inspiration",
|
||||||
rest = null,
|
rest = null,
|
||||||
cost = "Inspiration bardique",
|
cost = "Inspiration bardique",
|
||||||
effect = SkillItemUio.Dice(icon = R.drawable.ic_d6_24, label = "2d6"),
|
effect = SkillItemUio.Action.Dice(icon = R.drawable.ic_d6_24, label = "2d6"),
|
||||||
value = null,
|
value = null,
|
||||||
max = null,
|
max = null,
|
||||||
haveDetail = true,
|
haveDetail = true,
|
||||||
|
|
|
||||||
|
|
@ -37,6 +37,7 @@ import com.pixelized.rplexicon.R
|
||||||
import com.pixelized.rplexicon.data.model.Spell
|
import com.pixelized.rplexicon.data.model.Spell
|
||||||
import com.pixelized.rplexicon.ui.composable.AsyncImage
|
import com.pixelized.rplexicon.ui.composable.AsyncImage
|
||||||
import com.pixelized.rplexicon.ui.screens.character.composable.common.DiceButton
|
import com.pixelized.rplexicon.ui.screens.character.composable.common.DiceButton
|
||||||
|
import com.pixelized.rplexicon.ui.screens.character.composable.common.FlatValue
|
||||||
import com.pixelized.rplexicon.ui.theme.LexiconTheme
|
import com.pixelized.rplexicon.ui.theme.LexiconTheme
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.local.icon
|
import com.pixelized.rplexicon.utilitary.extentions.local.icon
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.uri
|
import com.pixelized.rplexicon.utilitary.extentions.uri
|
||||||
|
|
@ -50,16 +51,25 @@ data class SpellUio(
|
||||||
val castingTime: String,
|
val castingTime: String,
|
||||||
val range: String,
|
val range: String,
|
||||||
val duration: String,
|
val duration: String,
|
||||||
val hit: Dice?,
|
val hit: Action?,
|
||||||
val effect: Dice?,
|
val effect: Action?,
|
||||||
val changeWithLevel: Boolean,
|
val changeWithLevel: Boolean,
|
||||||
val isWarlock: Boolean,
|
val isWarlock: Boolean,
|
||||||
val ritual: Boolean,
|
val ritual: Boolean,
|
||||||
) {
|
) {
|
||||||
class Dice(
|
@Stable
|
||||||
@DrawableRes val icon: Int,
|
sealed class Action {
|
||||||
val label: String,
|
@Stable
|
||||||
)
|
class Dice(
|
||||||
|
@DrawableRes val icon: Int,
|
||||||
|
val label: String,
|
||||||
|
) : Action()
|
||||||
|
|
||||||
|
@Stable
|
||||||
|
class Flat(
|
||||||
|
val label: String,
|
||||||
|
) : Action()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@OptIn(ExperimentalLayoutApi::class)
|
@OptIn(ExperimentalLayoutApi::class)
|
||||||
|
|
@ -173,14 +183,20 @@ fun Spell(
|
||||||
Row(
|
Row(
|
||||||
horizontalArrangement = Arrangement.spacedBy(space = 4.dp),
|
horizontalArrangement = Arrangement.spacedBy(space = 4.dp),
|
||||||
) {
|
) {
|
||||||
spell.hit?.let { dice ->
|
spell.hit?.let { action ->
|
||||||
DiceButton(
|
when (action) {
|
||||||
icon = dice.icon,
|
is SpellUio.Action.Dice -> DiceButton(
|
||||||
text = dice.label,
|
icon = action.icon,
|
||||||
onClick = { spell.name.let(onHit) }
|
text = action.label,
|
||||||
)
|
onClick = { spell.name.let(onHit) }
|
||||||
|
)
|
||||||
|
|
||||||
|
is SpellUio.Action.Flat -> FlatValue(
|
||||||
|
text = action.label,
|
||||||
|
)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
spell.effect?.let { dice ->
|
spell.effect?.let { action ->
|
||||||
when {
|
when {
|
||||||
spell.changeWithLevel && spell.isWarlock.not() -> {
|
spell.changeWithLevel && spell.isWarlock.not() -> {
|
||||||
OutlinedButton(
|
OutlinedButton(
|
||||||
|
|
@ -196,19 +212,33 @@ fun Spell(
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
spell.changeWithLevel && spell.isWarlock -> {
|
spell.changeWithLevel && spell.isWarlock -> {
|
||||||
DiceButton(
|
when (action) {
|
||||||
icon = dice.icon,
|
is SpellUio.Action.Dice -> DiceButton(
|
||||||
text = dice.label,
|
icon = action.icon,
|
||||||
onClick = { onCast(spell.name) },
|
text = action.label,
|
||||||
)
|
onClick = { onCast(spell.name) },
|
||||||
|
)
|
||||||
|
|
||||||
|
is SpellUio.Action.Flat -> FlatValue(
|
||||||
|
text = action.label,
|
||||||
|
)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
else -> {
|
else -> {
|
||||||
DiceButton(
|
when (action) {
|
||||||
icon = dice.icon,
|
is SpellUio.Action.Dice -> DiceButton(
|
||||||
text = dice.label,
|
icon = action.icon,
|
||||||
onClick = { spell.name.let(onEffect) }
|
text = action.label,
|
||||||
)
|
onClick = { spell.name.let(onEffect) }
|
||||||
|
)
|
||||||
|
|
||||||
|
is SpellUio.Action.Flat -> FlatValue(
|
||||||
|
text = action.label,
|
||||||
|
)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -246,11 +276,11 @@ private class SpellPreviewProvider : PreviewParameterProvider<SpellUio> {
|
||||||
castingTime = "1 action",
|
castingTime = "1 action",
|
||||||
range = "36 mêtres",
|
range = "36 mêtres",
|
||||||
duration = "instantanée",
|
duration = "instantanée",
|
||||||
hit = SpellUio.Dice(
|
hit = SpellUio.Action.Dice(
|
||||||
icon = R.drawable.ic_d20_24,
|
icon = R.drawable.ic_d20_24,
|
||||||
label = "1d20+6",
|
label = "1d20+6",
|
||||||
),
|
),
|
||||||
effect = SpellUio.Dice(
|
effect = SpellUio.Action.Dice(
|
||||||
icon = R.drawable.ic_d10_24,
|
icon = R.drawable.ic_d10_24,
|
||||||
label = "1d10",
|
label = "1d10",
|
||||||
),
|
),
|
||||||
|
|
@ -267,7 +297,7 @@ private class SpellPreviewProvider : PreviewParameterProvider<SpellUio> {
|
||||||
range = "18 mêtres",
|
range = "18 mêtres",
|
||||||
duration = "instantanée",
|
duration = "instantanée",
|
||||||
hit = null,
|
hit = null,
|
||||||
effect = SpellUio.Dice(
|
effect = SpellUio.Action.Dice(
|
||||||
icon = R.drawable.ic_d10_24,
|
icon = R.drawable.ic_d10_24,
|
||||||
label = "1d4",
|
label = "1d4",
|
||||||
),
|
),
|
||||||
|
|
@ -284,7 +314,7 @@ private class SpellPreviewProvider : PreviewParameterProvider<SpellUio> {
|
||||||
range = "contact",
|
range = "contact",
|
||||||
duration = "instantanée",
|
duration = "instantanée",
|
||||||
hit = null,
|
hit = null,
|
||||||
effect = SpellUio.Dice(
|
effect = SpellUio.Action.Dice(
|
||||||
icon = R.drawable.ic_d8_24,
|
icon = R.drawable.ic_d8_24,
|
||||||
label = "1d8+3",
|
label = "1d8+3",
|
||||||
),
|
),
|
||||||
|
|
@ -301,7 +331,7 @@ private class SpellPreviewProvider : PreviewParameterProvider<SpellUio> {
|
||||||
range = "contact",
|
range = "contact",
|
||||||
duration = "instantanée",
|
duration = "instantanée",
|
||||||
hit = null,
|
hit = null,
|
||||||
effect = SpellUio.Dice(
|
effect = SpellUio.Action.Dice(
|
||||||
icon = R.drawable.ic_d8_24,
|
icon = R.drawable.ic_d8_24,
|
||||||
label = "1d8+3",
|
label = "1d8+3",
|
||||||
),
|
),
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,42 @@
|
||||||
|
package com.pixelized.rplexicon.ui.screens.character.composable.common
|
||||||
|
|
||||||
|
import android.content.res.Configuration
|
||||||
|
import androidx.compose.foundation.layout.Column
|
||||||
|
import androidx.compose.material3.MaterialTheme
|
||||||
|
import androidx.compose.material3.Surface
|
||||||
|
import androidx.compose.material3.Text
|
||||||
|
import androidx.compose.material3.minimumInteractiveComponentSize
|
||||||
|
import androidx.compose.runtime.Composable
|
||||||
|
import androidx.compose.ui.Alignment
|
||||||
|
import androidx.compose.ui.Modifier
|
||||||
|
import androidx.compose.ui.tooling.preview.Preview
|
||||||
|
import com.pixelized.rplexicon.ui.theme.LexiconTheme
|
||||||
|
|
||||||
|
@Composable
|
||||||
|
fun FlatValue(
|
||||||
|
modifier: Modifier = Modifier,
|
||||||
|
text: String,
|
||||||
|
) {
|
||||||
|
Column(
|
||||||
|
modifier = modifier.minimumInteractiveComponentSize(),
|
||||||
|
horizontalAlignment = Alignment.CenterHorizontally,
|
||||||
|
) {
|
||||||
|
Text(
|
||||||
|
style = MaterialTheme.typography.titleLarge,
|
||||||
|
text = text,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Composable
|
||||||
|
@Preview(uiMode = Configuration.UI_MODE_NIGHT_NO)
|
||||||
|
@Preview(uiMode = Configuration.UI_MODE_NIGHT_YES)
|
||||||
|
private fun DiceButtonPreview() {
|
||||||
|
LexiconTheme {
|
||||||
|
Surface {
|
||||||
|
FlatValue(
|
||||||
|
text = "5",
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -17,16 +17,15 @@ fun rememberAttackListStatePreview(): State<List<AttackUio>> = remember {
|
||||||
listOf(
|
listOf(
|
||||||
AttackUio(
|
AttackUio(
|
||||||
icon = R.drawable.ic_crossed_swords_24.uri.toUri(),
|
icon = R.drawable.ic_crossed_swords_24.uri.toUri(),
|
||||||
name = "Dagger",
|
name = "Unarmed attack",
|
||||||
type = R.string.attack_type_melee,
|
type = R.string.attack_type_melee,
|
||||||
range = "5 ft reach",
|
range = "5 ft reach",
|
||||||
hit = AttackUio.Dice(
|
hit = AttackUio.Action.Dice(
|
||||||
icon = R.drawable.ic_d20_24,
|
icon = R.drawable.ic_d20_24,
|
||||||
label = "1d20",
|
label = "1d20",
|
||||||
),
|
),
|
||||||
damage = AttackUio.Dice(
|
damage = AttackUio.Action.Flat(
|
||||||
icon = R.drawable.ic_d8_24,
|
label = "5",
|
||||||
label = "1d8",
|
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
AttackUio(
|
AttackUio(
|
||||||
|
|
@ -34,11 +33,11 @@ fun rememberAttackListStatePreview(): State<List<AttackUio>> = remember {
|
||||||
name = "Long bow",
|
name = "Long bow",
|
||||||
type = R.string.attack_type_range,
|
type = R.string.attack_type_range,
|
||||||
range = "30 ft reach",
|
range = "30 ft reach",
|
||||||
hit = AttackUio.Dice(
|
hit = AttackUio.Action.Dice(
|
||||||
icon = R.drawable.ic_d20_24,
|
icon = R.drawable.ic_d20_24,
|
||||||
label = "1d20+5",
|
label = "1d20+5",
|
||||||
),
|
),
|
||||||
damage = AttackUio.Dice(
|
damage = AttackUio.Action.Dice(
|
||||||
icon = R.drawable.ic_d8_24,
|
icon = R.drawable.ic_d8_24,
|
||||||
label = "1d8+3"
|
label = "1d8+3"
|
||||||
),
|
),
|
||||||
|
|
|
||||||
|
|
@ -30,11 +30,11 @@ fun rememberSpellListStatePreview(): State<List<Pair<SpellHeaderUio, List<SpellU
|
||||||
castingTime = "1 action",
|
castingTime = "1 action",
|
||||||
range = "36 mêtres",
|
range = "36 mêtres",
|
||||||
duration = "instantanée",
|
duration = "instantanée",
|
||||||
hit = SpellUio.Dice(
|
hit = SpellUio.Action.Dice(
|
||||||
icon = R.drawable.ic_d20_24,
|
icon = R.drawable.ic_d20_24,
|
||||||
label = "1d20+6",
|
label = "1d20+6",
|
||||||
),
|
),
|
||||||
effect = SpellUio.Dice(
|
effect = SpellUio.Action.Dice(
|
||||||
icon = R.drawable.ic_d10_24,
|
icon = R.drawable.ic_d10_24,
|
||||||
label = "1d10",
|
label = "1d10",
|
||||||
),
|
),
|
||||||
|
|
@ -51,7 +51,7 @@ fun rememberSpellListStatePreview(): State<List<Pair<SpellHeaderUio, List<SpellU
|
||||||
range = "18 mêtres",
|
range = "18 mêtres",
|
||||||
duration = "instantanée",
|
duration = "instantanée",
|
||||||
hit = null,
|
hit = null,
|
||||||
effect = SpellUio.Dice(
|
effect = SpellUio.Action.Dice(
|
||||||
icon = R.drawable.ic_d10_24,
|
icon = R.drawable.ic_d10_24,
|
||||||
label = "1d4",
|
label = "1d4",
|
||||||
),
|
),
|
||||||
|
|
@ -73,7 +73,7 @@ fun rememberSpellListStatePreview(): State<List<Pair<SpellHeaderUio, List<SpellU
|
||||||
range = "contact",
|
range = "contact",
|
||||||
duration = "instantanée",
|
duration = "instantanée",
|
||||||
hit = null,
|
hit = null,
|
||||||
effect = SpellUio.Dice(
|
effect = SpellUio.Action.Dice(
|
||||||
icon = R.drawable.ic_d8_24,
|
icon = R.drawable.ic_d8_24,
|
||||||
label = "1d8+3",
|
label = "1d8+3",
|
||||||
),
|
),
|
||||||
|
|
|
||||||
|
|
@ -1,14 +1,14 @@
|
||||||
package com.pixelized.rplexicon.ui.screens.character.factory
|
package com.pixelized.rplexicon.ui.screens.character.factory
|
||||||
|
|
||||||
import com.pixelized.rplexicon.R
|
import com.pixelized.rplexicon.R
|
||||||
import com.pixelized.rplexicon.data.model.alteration.Alteration
|
|
||||||
import com.pixelized.rplexicon.data.model.Attack
|
import com.pixelized.rplexicon.data.model.Attack
|
||||||
import com.pixelized.rplexicon.data.model.CharacterSheet
|
import com.pixelized.rplexicon.data.model.CharacterSheet
|
||||||
import com.pixelized.rplexicon.data.model.Property
|
import com.pixelized.rplexicon.data.model.Property
|
||||||
|
import com.pixelized.rplexicon.data.model.alteration.Alteration
|
||||||
import com.pixelized.rplexicon.ui.screens.character.composable.actions.AttackUio
|
import com.pixelized.rplexicon.ui.screens.character.composable.actions.AttackUio
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.icon
|
import com.pixelized.rplexicon.utilitary.extentions.icon
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.toLabel
|
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.modifier
|
import com.pixelized.rplexicon.utilitary.extentions.modifier
|
||||||
|
import com.pixelized.rplexicon.utilitary.extentions.toLabel
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
class AttackUioFactory @Inject constructor() {
|
class AttackUioFactory @Inject constructor() {
|
||||||
|
|
@ -31,12 +31,18 @@ class AttackUioFactory @Inject constructor() {
|
||||||
Property.DEXTERITY -> characterSheet.dexterity.modifier
|
Property.DEXTERITY -> characterSheet.dexterity.modifier
|
||||||
else -> 0
|
else -> 0
|
||||||
}
|
}
|
||||||
} + hitAlteration
|
} + hitAlteration + (diceThrow.flat?.value ?: 0)
|
||||||
// Build the UIO.
|
// Build the UIO.
|
||||||
AttackUio.Dice(
|
when (diceThrow.dice) {
|
||||||
icon = diceThrow.dice.icon,
|
null -> AttackUio.Action.Flat(
|
||||||
label = "${diceThrow.dice.toLabel()}${modifier.toLabel(true)}",
|
label = "$modifier",
|
||||||
)
|
)
|
||||||
|
|
||||||
|
else -> AttackUio.Action.Dice(
|
||||||
|
icon = diceThrow.dice.icon,
|
||||||
|
label = "${diceThrow.dice.toLabel()}${modifier.toLabel(true)}",
|
||||||
|
)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
val damage = attack.damage?.let { diceThrow ->
|
val damage = attack.damage?.let { diceThrow ->
|
||||||
|
|
@ -52,12 +58,18 @@ class AttackUioFactory @Inject constructor() {
|
||||||
Property.DEXTERITY -> characterSheet.dexterity.modifier
|
Property.DEXTERITY -> characterSheet.dexterity.modifier
|
||||||
else -> 0
|
else -> 0
|
||||||
}
|
}
|
||||||
} + damageAlteration
|
} + damageAlteration + (diceThrow.flat?.value ?: 0)
|
||||||
// Build the UIO.
|
// Build the UIO.
|
||||||
AttackUio.Dice(
|
when (diceThrow.dice) {
|
||||||
icon = diceThrow.dice.icon,
|
null -> AttackUio.Action.Flat(
|
||||||
label = "${diceThrow.dice.toLabel()}${modifier.toLabel(true)}",
|
label = "$modifier",
|
||||||
)
|
)
|
||||||
|
|
||||||
|
else -> AttackUio.Action.Dice(
|
||||||
|
icon = diceThrow.dice.icon,
|
||||||
|
label = "${diceThrow.dice.toLabel()}${modifier.toLabel(true)}"
|
||||||
|
)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return AttackUio(
|
return AttackUio(
|
||||||
|
|
|
||||||
|
|
@ -7,11 +7,11 @@ import com.pixelized.rplexicon.data.network.CharacterSheetFire
|
||||||
import com.pixelized.rplexicon.data.repository.character.DescriptionRepository
|
import com.pixelized.rplexicon.data.repository.character.DescriptionRepository
|
||||||
import com.pixelized.rplexicon.ui.screens.character.composable.actions.SkillItemUio
|
import com.pixelized.rplexicon.ui.screens.character.composable.actions.SkillItemUio
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.icon
|
import com.pixelized.rplexicon.utilitary.extentions.icon
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.toLabel
|
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.local.base
|
import com.pixelized.rplexicon.utilitary.extentions.local.base
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.local.primary
|
import com.pixelized.rplexicon.utilitary.extentions.local.primary
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.local.secondary
|
import com.pixelized.rplexicon.utilitary.extentions.local.secondary
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.modifier
|
import com.pixelized.rplexicon.utilitary.extentions.modifier
|
||||||
|
import com.pixelized.rplexicon.utilitary.extentions.toLabel
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
class SkillFactoryUioFactory @Inject constructor(
|
class SkillFactoryUioFactory @Inject constructor(
|
||||||
|
|
@ -49,11 +49,17 @@ class SkillFactoryUioFactory @Inject constructor(
|
||||||
translate = description?.original,
|
translate = description?.original,
|
||||||
rest = skill.rest,
|
rest = skill.rest,
|
||||||
cost = skill.cost,
|
cost = skill.cost,
|
||||||
effect = skill.effect?.let {
|
effect = when {
|
||||||
SkillItemUio.Dice(
|
skill.effect?.dice != null -> SkillItemUio.Action.Dice(
|
||||||
icon = it.dice.icon,
|
icon = skill.effect.dice.icon,
|
||||||
label = "${skill.effect.dice.toLabel()}${modifier.toLabel(true)}",
|
label = "${skill.effect.dice.toLabel()}${modifier.toLabel(true)}",
|
||||||
)
|
)
|
||||||
|
|
||||||
|
skill.effect != null -> SkillItemUio.Action.Flat(
|
||||||
|
label = "$modifier",
|
||||||
|
)
|
||||||
|
|
||||||
|
else -> null
|
||||||
},
|
},
|
||||||
value = fire?.skills?.get(skill.name) ?: 0,
|
value = fire?.skills?.get(skill.name) ?: 0,
|
||||||
max = skill.amount,
|
max = skill.amount,
|
||||||
|
|
|
||||||
|
|
@ -1,13 +1,14 @@
|
||||||
package com.pixelized.rplexicon.ui.screens.character.factory
|
package com.pixelized.rplexicon.ui.screens.character.factory
|
||||||
|
|
||||||
|
import com.pixelized.rplexicon.R
|
||||||
import com.pixelized.rplexicon.data.model.AssignedSpell
|
import com.pixelized.rplexicon.data.model.AssignedSpell
|
||||||
import com.pixelized.rplexicon.data.model.CharacterSheet
|
import com.pixelized.rplexicon.data.model.CharacterSheet
|
||||||
import com.pixelized.rplexicon.data.model.Property
|
import com.pixelized.rplexicon.data.model.Property
|
||||||
import com.pixelized.rplexicon.data.repository.character.DescriptionRepository
|
import com.pixelized.rplexicon.data.repository.character.DescriptionRepository
|
||||||
import com.pixelized.rplexicon.ui.screens.character.composable.actions.SpellUio
|
import com.pixelized.rplexicon.ui.screens.character.composable.actions.SpellUio
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.icon
|
import com.pixelized.rplexicon.utilitary.extentions.icon
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.toLabel
|
|
||||||
import com.pixelized.rplexicon.utilitary.extentions.modifier
|
import com.pixelized.rplexicon.utilitary.extentions.modifier
|
||||||
|
import com.pixelized.rplexicon.utilitary.extentions.toLabel
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
class SpellUioFactory @Inject constructor(
|
class SpellUioFactory @Inject constructor(
|
||||||
|
|
@ -28,11 +29,17 @@ class SpellUioFactory @Inject constructor(
|
||||||
Property.CHARISMA -> characterSheet.charisma.modifier
|
Property.CHARISMA -> characterSheet.charisma.modifier
|
||||||
else -> 0
|
else -> 0
|
||||||
}
|
}
|
||||||
|
} + (diceThrow.flat?.value ?: 0)
|
||||||
|
when (diceThrow.dice) {
|
||||||
|
null -> SpellUio.Action.Flat(
|
||||||
|
label = "$modifier",
|
||||||
|
)
|
||||||
|
|
||||||
|
else -> SpellUio.Action.Dice(
|
||||||
|
icon = diceThrow.dice.icon,
|
||||||
|
label = "${diceThrow.dice.toLabel()}${modifier.toLabel(true)}",
|
||||||
|
)
|
||||||
}
|
}
|
||||||
SpellUio.Dice(
|
|
||||||
icon = diceThrow.dice.icon,
|
|
||||||
label = "${diceThrow.dice.toLabel()}${modifier.toLabel(true)}",
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
val effect = assignedSpell.effect?.let { diceThrow ->
|
val effect = assignedSpell.effect?.let { diceThrow ->
|
||||||
val modifier = diceThrow.modifier.sumOf {
|
val modifier = diceThrow.modifier.sumOf {
|
||||||
|
|
@ -52,25 +59,38 @@ class SpellUioFactory @Inject constructor(
|
||||||
val delta = warlockSpellLevel?.minus(assignedSpell.spell.level) ?: 0
|
val delta = warlockSpellLevel?.minus(assignedSpell.spell.level) ?: 0
|
||||||
if (warlockSpellLevel == null || level == null || delta <= 0) {
|
if (warlockSpellLevel == null || level == null || delta <= 0) {
|
||||||
// default case of non warlock character of the spell don't scale
|
// default case of non warlock character of the spell don't scale
|
||||||
SpellUio.Dice(
|
when (diceThrow.dice) {
|
||||||
icon = diceThrow.dice.icon,
|
null -> SpellUio.Action.Flat(
|
||||||
label = "${diceThrow.dice.toLabel()}${modifier.toLabel(true)}",
|
label = "$modifier",
|
||||||
)
|
)
|
||||||
} else if (diceThrow.dice.faces == level.dice.faces) {
|
|
||||||
|
else -> SpellUio.Action.Dice(
|
||||||
|
icon = diceThrow.dice.icon,
|
||||||
|
label = "${diceThrow.dice.toLabel()}${modifier.toLabel(true)}",
|
||||||
|
)
|
||||||
|
}
|
||||||
|
} else if (diceThrow.dice?.faces == level.dice?.faces) {
|
||||||
// warlock character, upscale the spell to warlock spell level
|
// warlock character, upscale the spell to warlock spell level
|
||||||
val upscaleModifier = modifier + (level.flat?.value ?: 0) * delta
|
val upscaleModifier = modifier + (level.flat?.value ?: 0) * delta
|
||||||
val diceCount = diceThrow.dice.count + level.dice.count * delta
|
val diceCount = (diceThrow.dice?.count ?: 0) + (level.dice?.count ?: 0) * delta
|
||||||
SpellUio.Dice(
|
|
||||||
icon = diceThrow.dice.icon,
|
when (diceThrow.dice) {
|
||||||
label = "${diceCount}d${diceThrow.dice.faces}${upscaleModifier.toLabel(true)}",
|
null -> SpellUio.Action.Flat(
|
||||||
)
|
label = "$modifier",
|
||||||
|
)
|
||||||
|
|
||||||
|
else -> SpellUio.Action.Dice(
|
||||||
|
icon = diceThrow.dice.icon,
|
||||||
|
label = "${diceCount}d${diceThrow.dice.faces}${upscaleModifier.toLabel(true)}",
|
||||||
|
)
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
// warlock character, case where the dice use to upscale is not the one from the spell.
|
// warlock character, case where the dice use to upscale is not the one from the spell.
|
||||||
val deltaModifier = level.flat?.value?.times(delta) ?: 0
|
val deltaModifier = level.flat?.value?.times(delta) ?: 0
|
||||||
SpellUio.Dice(
|
SpellUio.Action.Dice(
|
||||||
icon = diceThrow.dice.icon,
|
icon = diceThrow.dice?.icon ?: R.drawable.ic_d4_24,
|
||||||
label = "${diceThrow.dice.toLabel()}${modifier.toLabel(true)}" +
|
label = "${diceThrow.dice?.toLabel()}${modifier.toLabel(true)}" +
|
||||||
"+ ${level.dice.count * delta}d${level.dice.faces}${deltaModifier.toLabel(true)}",
|
"+ ${level.dice?.count?.times(delta)}d${level.dice?.faces}${deltaModifier.toLabel(true)}",
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -180,7 +180,7 @@ class SpellsViewModel @Inject constructor(
|
||||||
val modifierLabel = modifier
|
val modifierLabel = modifier
|
||||||
.sumOf { modifier -> modifier.toValue(character = character) }
|
.sumOf { modifier -> modifier.toValue(character = character) }
|
||||||
.let { if (it != 0) "${it.signLabel}${abs(it) * level}" else "" }
|
.let { if (it != 0) "${it.signLabel}${abs(it) * level}" else "" }
|
||||||
return when (level > 0) {
|
return when (level > 0 && dice != null) {
|
||||||
true -> "${dice.count * level}d${dice.faces}${modifierLabel}"
|
true -> "${dice.count * level}d${dice.faces}${modifierLabel}"
|
||||||
else -> null
|
else -> null
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue