Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
28 commits
Select commit Hold shift + click to select a range
6f08bd9
command spell
ArthurKun21 Aug 15, 2024
cb70568
missing assets
ArthurKun21 Aug 15, 2024
fd21b1d
fix missing
ArthurKun21 Aug 15, 2024
ca6b3f4
forgot comma
ArthurKun21 Aug 15, 2024
1b69db8
fix
ArthurKun21 Aug 15, 2024
5bafd1a
convert stateflow to state
ArthurKun21 Aug 15, 2024
653627e
fix
ArthurKun21 Aug 15, 2024
33bdebc
Merge branch 'master' into cs-refill
ArthurKun21 Nov 25, 2024
426707d
fix the code
ArthurKun21 Nov 25, 2024
10d2b84
updated and fixed UI
ArthurKun21 Nov 25, 2024
971a1b3
Fix the spacing
ArthurKun21 Nov 25, 2024
db90866
Update the text used to return
ArthurKun21 Nov 25, 2024
4867d7b
Update the logic for CS usage tracking
ArthurKun21 Nov 25, 2024
97df649
Fix delete behavior
ArthurKun21 Nov 25, 2024
5aa17b6
Fix Command Spell Target
ArthurKun21 Nov 25, 2024
6dab617
Change the colors of the target buttons for Command Spell
ArthurKun21 Nov 26, 2024
dd36692
Updated UI to make the text more center
ArthurKun21 Nov 26, 2024
4b63eeb
Merge branch 'master' into cs-refill
ArthurKun21 Nov 28, 2024
bb3f48e
Improved detection
ArthurKun21 Dec 23, 2024
b7d7cb4
Merge branch 'master' into cs-refill
ArthurKun21 Jan 3, 2025
3b9fbf4
Merge branch 'master' into cs-refill
ArthurKun21 Jan 7, 2025
611964b
Merge branch 'master' into cs-refill
ArthurKun21 Jan 16, 2025
a35a996
Merge branch 'master' into cs-refill
ArthurKun21 Jan 30, 2025
983c939
Merge branch 'master' into cs-refill
ArthurKun21 May 13, 2025
edebab9
Merge branch 'master' into cs-refill
ArthurKun21 May 28, 2025
e98034b
feat: add CN template image for command spell
ArthurKun21 Aug 8, 2025
00edd44
Merge branch 'master' into cs-refill
ArthurKun21 Aug 8, 2025
b3d94f4
fix: update CN template image
ArthurKun21 Aug 8, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Binary file added app/src/main/assets/Cn/command_spell.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added app/src/main/assets/En/cancel.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added app/src/main/assets/En/command_spell.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added app/src/main/assets/Jp/command_spell.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,7 @@ private fun AutoBattle.ExitReason.text(): String = when (this) {
AutoBattle.ExitReason.FirstClearRewards -> stringResource(R.string.first_clear_rewards)
AutoBattle.ExitReason.Paused -> stringResource(R.string.script_paused)
AutoBattle.ExitReason.StopAfterThisRun -> stringResource(R.string.stop_after_this_run)
AutoBattle.ExitReason.OutOfCommandSpells -> stringResource(id = R.string.p_stop_on_out_of_command_spell)
}

@Composable
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -88,8 +88,9 @@ fun SkillMakerUI(
val wave by vm.wave

Crossfade(
current,
animationSpec = spring()
targetState = current,
animationSpec = spring(),
label = "Skill Maker Navigation Animation"
) { nav ->
when (nav) {
SkillMakerNav.Atk -> {
Expand All @@ -111,6 +112,9 @@ fun SkillMakerUI(
SkillMakerNav.Main -> {
SkillMakerMain(
vm = vm,
onCommandSpell = {
navigate(SkillMakerNav.CommandSpell(it))
},
onMasterSkills = { navigate(SkillMakerNav.MasterSkills) },
onAtk = { navigate(SkillMakerNav.Atk) },
onSkill = { vm.initSkill(it) },
Expand All @@ -131,6 +135,23 @@ fun SkillMakerUI(
)
}

is SkillMakerNav.CommandSpell -> {
SkillMakerCommandSpells(
remaining = nav.cs,
onCommandSpell = {
vm.initCommandSpell(it)
},
onBack = {
navigate(SkillMakerNav.Main)
}
)
}
is SkillMakerNav.CommandSpellTarget -> {
SkillMakerCommandSpellTarget(
onServantTarget = { vm.targetSkill(it) }
)
}

SkillMakerNav.OrderChange -> {
SkillMakerOrderChange(
onCommit = { starting, sub ->
Expand Down Expand Up @@ -181,6 +202,7 @@ fun SkillMakerUI(
is SkillMakerNav.Choice2Target -> {
SkillMakerChoice2Target(onSkillTarget = { vm.targetSkill(listOf(nav.firstTarget, it)) })
}

is SkillMakerNav.Choice3 -> {
SkillMakerChoice3(
slot = nav.slot,
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,165 @@
package io.github.fate_grand_automata.ui.skill_maker

import android.content.res.Configuration
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.fillMaxHeight
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.padding
import androidx.compose.material3.Button
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.res.colorResource
import androidx.compose.ui.res.stringResource
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.tooling.preview.Preview
import androidx.compose.ui.unit.dp
import io.github.fate_grand_automata.R
import io.github.fate_grand_automata.scripts.models.ServantTarget
import io.github.fate_grand_automata.scripts.models.Skill
import io.github.fate_grand_automata.ui.FGATheme
import io.github.fate_grand_automata.ui.FGATitle
import io.github.fate_grand_automata.ui.skill_maker.special.TargetButton
import io.github.fate_grand_automata.util.stringRes

@Composable
fun SkillMakerCommandSpells(
remaining: Int,
onCommandSpell: (Skill.CommandSpell) -> Unit,
onBack: () -> Unit
) {
Column(
modifier = Modifier
.fillMaxHeight()
.padding(16.dp)
) {
FGATitle(
stringResource(R.string.skill_maker_command_spell, remaining)
)

if (remaining > 0) {
Row(
modifier = Modifier
.weight(1f)
.fillMaxWidth(),
verticalAlignment = Alignment.CenterVertically,
horizontalArrangement = Arrangement.SpaceEvenly
) {
TargetButton(
onClick = {
onCommandSpell(Skill.CommandSpell.CS1)
},
color = colorResource(R.color.colorServant1),
text = stringResource(Skill.CommandSpell.CS1.stringRes)
)

TargetButton(
onClick = {
onCommandSpell(Skill.CommandSpell.CS2)
},
color = colorResource(R.color.colorServant2),
text = stringResource(Skill.CommandSpell.CS2.stringRes)
)
}
} else {
Row(
modifier = Modifier
.weight(1f)
.fillMaxWidth(),
horizontalArrangement = Arrangement.Center,
verticalAlignment = Alignment.CenterVertically
){
Text(
stringResource(R.string.skill_maker_command_spell_warning),
modifier = Modifier,
textAlign = TextAlign.Center
)
}

Row(
modifier = Modifier
.fillMaxWidth(),
horizontalArrangement = Arrangement.Center,
verticalAlignment = Alignment.CenterVertically
){
Button(
onClick = onBack,
) {
Text(stringResource(R.string.dismiss))
}
}
}
}
}

@Composable
fun SkillMakerCommandSpellTarget(
onServantTarget: (ServantTarget) -> Unit,
) {
Column(
modifier = Modifier
.fillMaxHeight()
.padding(16.dp)
) {
FGATitle(
stringResource(R.string.skill_maker_target_header)
)

Row(
horizontalArrangement = Arrangement.SpaceEvenly,
verticalAlignment = Alignment.CenterVertically,
modifier = Modifier
.weight(1f)
.fillMaxWidth()
) {
TargetButton(
onClick = { onServantTarget(ServantTarget.A) },
color = colorResource(R.color.colorServant1),
text = stringResource(R.string.skill_maker_target_servant, 1)
)

TargetButton(
onClick = { onServantTarget(ServantTarget.B) },
color = colorResource(R.color.colorServant2),
text = stringResource(R.string.skill_maker_target_servant, 2)
)

TargetButton(
onClick = { onServantTarget(ServantTarget.C) },
color = colorResource(R.color.colorServant3),
text = stringResource(R.string.skill_maker_target_servant, 3)
)
}
}
}


@Preview(name = "Light Mode", widthDp = 600, heightDp = 300)
@Preview(name = "Dark Mode", widthDp = 600, heightDp = 300, uiMode = Configuration.UI_MODE_NIGHT_YES)
@Composable
fun TestCommandSpell() {
FGATheme {
SkillMakerCommandSpells(
remaining = 3,
onCommandSpell = { },
onBack = { }
)
}
}

@Preview(name = "Light Mode", widthDp = 600, heightDp = 300)
@Preview(name = "Dark Mode", widthDp = 600, heightDp = 300, uiMode = Configuration.UI_MODE_NIGHT_YES)
@Composable
fun TestCommandSpellZero() {
FGATheme {
SkillMakerCommandSpells(
remaining = 0,
onCommandSpell = { },
onBack = { }
)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,7 @@ sealed class SkillMakerEntry {

is AutoSkillAction.ServantSkill -> toString(action.skill, action.targets)
is AutoSkillAction.MasterSkill -> toString(action.skill, action.target)
is AutoSkillAction.CommandSpell -> toString(action.skill, action.target)
is AutoSkillAction.TargetEnemy -> "${SpecialCommand.EnemyTarget.autoSkillCode}${action.enemy.autoSkillCode}"
is AutoSkillAction.OrderChange -> "${SpecialCommand.OrderChange.autoSkillCode}${action.starting.autoSkillCode}${action.sub.autoSkillCode}"
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ import androidx.compose.material3.ButtonDefaults
import androidx.compose.material3.RadioButton
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.getValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
Expand All @@ -46,6 +47,7 @@ import io.github.fate_grand_automata.ui.icon
@Composable
fun SkillMakerMain(
vm: SkillMakerViewModel,
onCommandSpell: (Int) -> Unit,
onMasterSkills: () -> Unit,
onAtk: () -> Unit,
onSkill: (Skill.Servant) -> Unit,
Expand Down Expand Up @@ -128,6 +130,8 @@ fun SkillMakerMain(
)
}

val commandSpellRemaining by vm.commandSpellRemaining.collectAsState()

Column(
verticalArrangement = Arrangement.Bottom,
horizontalAlignment = Alignment.End,
Expand All @@ -136,6 +140,22 @@ fun SkillMakerMain(
.width(IntrinsicSize.Max)
.fillMaxHeight()
) {

Button(
colors = ButtonDefaults.buttonColors(containerColor = colorResource(R.color.colorCommandSpell)),
onClick = {
onCommandSpell(commandSpellRemaining)
}
) {
Text(
stringResource(R.string.skill_maker_command_spell_title_short, commandSpellRemaining),
textAlign = TextAlign.Center,
color = Color.White
)
}

Spacer(Modifier.height(8.dp))

Button(
colors = ButtonDefaults.buttonColors(containerColor = colorResource(R.color.colorMasterSkill)),
onClick = onMasterSkills
Expand All @@ -147,7 +167,7 @@ fun SkillMakerMain(
)
}

Spacer(Modifier.height(16.dp))
Spacer(Modifier.height(8.dp))

Button(
shape = CircleShape,
Expand Down Expand Up @@ -247,6 +267,7 @@ val SkillMakerEntry?.colorRes: Int
'g', 'h', 'i' -> R.color.colorServant3
else -> defaultColor
}
is AutoSkillAction.CommandSpell -> R.color.colorCommandSpell

else -> defaultColor
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ sealed class SkillMakerNav {
data object Atk : SkillMakerNav()
data object OrderChange : SkillMakerNav()
data class SkillTarget(val skill: Skill) : SkillMakerNav()
data class CommandSpell(val cs: Int) : SkillMakerNav()
data class CommandSpellTarget(val skill: Skill) : SkillMakerNav()
data class ChangeNpType2(val skill: Skill) : SkillMakerNav()
data class ChangeNpType3(val skill: Skill) : SkillMakerNav()
data class Choice2(val skill: Skill, val slot: SkillSlot) : SkillMakerNav()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -295,6 +295,7 @@ fun SkillMakerTarget(
}
}


@Composable
private fun ButtonWithHint(
onClick: () -> Unit,
Expand Down
Loading