diff --git a/app/src/main/java/com/github/nacabaro/vbhelper/battle/ArenaBattleSystem.kt b/app/src/main/java/com/github/nacabaro/vbhelper/battle/ArenaBattleSystem.kt index 6105bd3..61073fe 100644 --- a/app/src/main/java/com/github/nacabaro/vbhelper/battle/ArenaBattleSystem.kt +++ b/app/src/main/java/com/github/nacabaro/vbhelper/battle/ArenaBattleSystem.kt @@ -5,6 +5,7 @@ import androidx.compose.runtime.MutableState import androidx.compose.runtime.mutableStateOf import androidx.compose.runtime.getValue import androidx.compose.runtime.setValue +import androidx.compose.runtime.State class ArenaBattleSystem { companion object { @@ -85,6 +86,20 @@ class ArenaBattleSystem { private var _isOpponentHit by mutableStateOf(false) val isOpponentHit: Boolean get() = _isOpponentHit + // Delayed hit states for SLEEP animation timing + private var _isPlayerHitDelayed by mutableStateOf(false) + val isPlayerHitDelayed: Boolean get() = _isPlayerHitDelayed + + private var _isOpponentHitDelayed by mutableStateOf(false) + val isOpponentHitDelayed: Boolean get() = _isOpponentHitDelayed + + // Delayed shake states for shake animation timing + private var _isPlayerShakeDelayed by mutableStateOf(false) + val isPlayerShakeDelayed: Boolean get() = _isPlayerShakeDelayed + + private var _isOpponentShakeDelayed by mutableStateOf(false) + val isOpponentShakeDelayed: Boolean get() = _isOpponentShakeDelayed + // Counter-attack tracking private var _shouldCounterAttack by mutableStateOf(false) val shouldCounterAttack: Boolean get() = _shouldCounterAttack @@ -187,6 +202,10 @@ class ArenaBattleSystem { _opponentDodgeDirection = 1f _isPlayerHit = false _isOpponentHit = false + _isPlayerHitDelayed = false + _isOpponentHitDelayed = false + _isPlayerShakeDelayed = false + _isOpponentShakeDelayed = false _shouldCounterAttack = false _counterAttackIsHit = false _opponentAttackIsHit = false @@ -297,12 +316,22 @@ class ArenaBattleSystem { Log.d(TAG, "Started player hit animation") } + fun startPlayerHitDelayed() { + _isPlayerHitDelayed = true + Log.d(TAG, "Started delayed player hit animation") + } + fun endPlayerHit() { _isPlayerHit = false _hitProgress = 0f Log.d(TAG, "Ended player hit animation") } + fun endPlayerHitDelayed() { + _isPlayerHitDelayed = false + Log.d(TAG, "Ended delayed player hit animation") + } + // Opponent-specific hit methods fun startOpponentHit() { _isOpponentHit = true @@ -310,12 +339,43 @@ class ArenaBattleSystem { Log.d(TAG, "Started opponent hit animation") } + fun startOpponentHitDelayed() { + _isOpponentHitDelayed = true + Log.d(TAG, "Started delayed opponent hit animation") + } + fun endOpponentHit() { _isOpponentHit = false _hitProgress = 0f Log.d(TAG, "Ended opponent hit animation") } + fun endOpponentHitDelayed() { + _isOpponentHitDelayed = false + Log.d(TAG, "Ended delayed opponent hit animation") + } + + // Delayed shake methods + fun startPlayerShakeDelayed() { + _isPlayerShakeDelayed = true + Log.d(TAG, "Started delayed player shake animation") + } + + fun endPlayerShakeDelayed() { + _isPlayerShakeDelayed = false + Log.d(TAG, "Ended delayed player shake animation") + } + + fun startOpponentShakeDelayed() { + _isOpponentShakeDelayed = true + Log.d(TAG, "Started delayed opponent shake animation") + } + + fun endOpponentShakeDelayed() { + _isOpponentShakeDelayed = false + Log.d(TAG, "Ended delayed opponent shake animation") + } + // Combined method to handle attack result fun handleAttackResult(isHit: Boolean) { _attackIsHit = isHit diff --git a/app/src/main/java/com/github/nacabaro/vbhelper/screens/BattlesScreen.kt b/app/src/main/java/com/github/nacabaro/vbhelper/screens/BattlesScreen.kt index 412fd25..e0b808d 100644 --- a/app/src/main/java/com/github/nacabaro/vbhelper/screens/BattlesScreen.kt +++ b/app/src/main/java/com/github/nacabaro/vbhelper/screens/BattlesScreen.kt @@ -179,7 +179,11 @@ fun BattleScreen( showOpponentHitEffect = false hidePlayerAttackSprite = false hideEnemyAttackSprite = false - println("DEBUG: Reset hit effect states - attack phase returned to idle") + battleSystem.endPlayerHitDelayed() + battleSystem.endOpponentHitDelayed() + battleSystem.endPlayerShakeDelayed() + battleSystem.endOpponentShakeDelayed() + println("DEBUG: Reset hit effect states, attack sprite visibility, and delayed hit states") } } @@ -240,6 +244,18 @@ fun BattleScreen( println("DEBUG: Showing opponent damage number after delay") } } + // Delay SLEEP animation to match hit effect timing + coroutineScope.launch { + delay(400) // Match the hit effect delay + battleSystem.startOpponentHitDelayed() + println("DEBUG: Starting delayed opponent hit animation") + } + // Delay shake animation to match hit effect timing + coroutineScope.launch { + delay(400) // Match the hit effect delay + battleSystem.startOpponentShakeDelayed() + println("DEBUG: Starting delayed opponent shake animation") + } } else { // Player attack misses, enemy dodges println("Player attack misses, enemy dodges at progress $progress") @@ -305,6 +321,18 @@ fun BattleScreen( println("DEBUG: Showing player damage number after delay") } } + // Delay SLEEP animation to match hit effect timing + coroutineScope.launch { + delay(400) // Match the hit effect delay + battleSystem.startPlayerHitDelayed() + println("DEBUG: Starting delayed player hit animation") + } + // Delay shake animation to match hit effect timing + coroutineScope.launch { + delay(400) // Match the hit effect delay + battleSystem.startPlayerShakeDelayed() + println("DEBUG: Starting delayed player shake animation") + } } else { // Enemy attack misses, player dodges println("Enemy attack misses, player dodges at progress $progress") @@ -424,6 +452,26 @@ fun BattleScreen( } } + // Player delayed shake animation + LaunchedEffect(battleSystem.isPlayerShakeDelayed) { + if (battleSystem.isPlayerShakeDelayed) { + println("Starting delayed player shake animation") + var hitProgress = 0f + + // Quick hit effect + while (hitProgress < 1f) { + hitProgress += 0.1f // Fast hit effect + battleSystem.setHitProgress(hitProgress) + delay(16) + } + + delay(100) // Brief pause + + battleSystem.endPlayerShakeDelayed() + println("Delayed player shake animation completed") + } + } + // Opponent hit animation LaunchedEffect(battleSystem.isOpponentHit) { if (battleSystem.isOpponentHit) { @@ -444,6 +492,26 @@ fun BattleScreen( } } + // Opponent delayed shake animation + LaunchedEffect(battleSystem.isOpponentShakeDelayed) { + if (battleSystem.isOpponentShakeDelayed) { + println("Starting delayed opponent shake animation") + var hitProgress = 0f + + // Quick hit effect + while (hitProgress < 1f) { + hitProgress += 0.1f // Fast hit effect + battleSystem.setHitProgress(hitProgress) + delay(16) + } + + delay(100) // Brief pause + + battleSystem.endOpponentShakeDelayed() + println("Delayed opponent shake animation completed") + } + } + // Damage number handling - store pending damage but don't show immediately LaunchedEffect(pendingPlayerDamage) { if (pendingPlayerDamage > 0) { @@ -721,7 +789,7 @@ fun MiddleBattleView( val enemyAnimationType = when { battleSystem.attackPhase == 1 -> DigimonAnimationType.ATTACK // Both attacking in Phase 1 battleSystem.isOpponentDodging -> DigimonAnimationType.WALK - battleSystem.isOpponentHit -> DigimonAnimationType.SLEEP + battleSystem.isOpponentHitDelayed -> DigimonAnimationType.SLEEP else -> DigimonAnimationType.IDLE } @@ -741,7 +809,7 @@ fun MiddleBattleView( } // Calculate hit effect for enemy - val enemyHitOffset = if (battleSystem.isOpponentHit) { + val enemyHitOffset = if (battleSystem.isOpponentShakeDelayed) { val shakeAmount = 5.dp val progress = battleSystem.hitProgress val shake = if (progress < 0.5f) progress * 2f else (1f - progress) * 2f @@ -802,7 +870,7 @@ fun MiddleBattleView( val playerAnimationType = when { battleSystem.attackPhase == 1 -> DigimonAnimationType.ATTACK // Both attacking in Phase 1 battleSystem.isPlayerDodging -> DigimonAnimationType.WALK - battleSystem.isPlayerHit -> DigimonAnimationType.SLEEP + battleSystem.isPlayerHitDelayed -> DigimonAnimationType.SLEEP else -> DigimonAnimationType.IDLE } @@ -822,7 +890,7 @@ fun MiddleBattleView( } // Calculate hit effect for player - val playerHitOffset = if (battleSystem.isPlayerHit) { + val playerHitOffset = if (battleSystem.isPlayerShakeDelayed) { val shakeAmount = 5.dp val progress = battleSystem.hitProgress val shake = if (progress < 0.5f) progress * 2f else (1f - progress) * 2f @@ -1135,7 +1203,7 @@ fun PlayerBattleView( // Determine animation type based on battle state val animationType = when { battleSystem.isPlayerDodging -> DigimonAnimationType.WALK // Use walk animation for dodge - battleSystem.isPlayerHit -> DigimonAnimationType.SLEEP // Use sleep animation for hit effect (injured sprite) + battleSystem.isPlayerHitDelayed -> DigimonAnimationType.SLEEP // Use sleep animation for hit effect (injured sprite) battleSystem.attackPhase == 1 -> DigimonAnimationType.ATTACK // Player attack on player screen battleSystem.attackPhase == 2 -> DigimonAnimationType.ATTACK // Player attack on opponent screen battleSystem.attackPhase == 3 -> DigimonAnimationType.IDLE // Opponent attack on opponent screen @@ -1161,7 +1229,7 @@ fun PlayerBattleView( } // Calculate hit effect (slight shake) - val hitOffset = if (battleSystem.isPlayerHit) { + val hitOffset = if (battleSystem.isPlayerShakeDelayed) { val shakeAmount = 5.dp val progress = battleSystem.hitProgress // Simple shake effect without complex math @@ -1448,7 +1516,7 @@ fun EnemyBattleView( // Determine animation type based on battle state val animationType = when { battleSystem.isOpponentDodging -> DigimonAnimationType.WALK // Use walk animation for dodge - battleSystem.isOpponentHit -> DigimonAnimationType.SLEEP // Use sleep animation for hit effect (injured sprite) + battleSystem.isOpponentHitDelayed -> DigimonAnimationType.SLEEP // Use sleep animation for hit effect (injured sprite) battleSystem.attackPhase == 2 -> DigimonAnimationType.IDLE // Player attack on enemy screen else -> DigimonAnimationType.IDLE } @@ -1471,7 +1539,7 @@ fun EnemyBattleView( } // Calculate hit effect (slight shake) - val hitOffset = if (battleSystem.isOpponentHit) { + val hitOffset = if (battleSystem.isOpponentShakeDelayed) { val shakeAmount = 5.dp val progress = battleSystem.hitProgress // Simple shake effect without complex math