diff --git a/hwe/process_war.ng.php b/hwe/process_war.ng.php index eb504e44..41d5fb1f 100644 --- a/hwe/process_war.ng.php +++ b/hwe/process_war.ng.php @@ -35,10 +35,16 @@ function processWar_NG( $defender = $city; if($city->getRawNation()['rice'] <= 0 && $city->getRaw()['supply'] == 1){ + //병량 패퇴 $attacker->setOppose($defender); $defender->setOppose($attacker); + $attacker->addTrain(1); + $attacker->addWin(); + $defender->addLose(); + $defender->heavyDecreseWealth(); + $conquerCity = true; break; } @@ -130,18 +136,25 @@ function processWar_NG( $attacker->increaseKilled($deadDefender); $defender->increaseKilled($deadAttacker); - //TODO: 쌀 소모 반영등은 이전 코드와 달리 동적으로 매 페이즈마다 추가 계산 + //NOTE: 기술, 도시 사망자 수는 '전투 종료 후' 외부에서 반영. - //TODO: 로그 출력 + $phaseNickname = $currPhase + 1; + $attacker->getLogger()->pushGeneralBattleDetailLog( + "$phaseNickname : 【{$attacker->getName()}】 {$attacker->getHP()} (-$deadAttacker) VS {$defender->getHP()} (-$deadDefender) 【{$defender->getName()}】" + ); + + $defender->getLogger()->pushGeneralBattleDetailLog( + "$phaseNickname : 【{$defender->getName()}】 {$defender->getHP()} (-$deadDefender) VS {$attacker->getHP()} (-$deadAttacker) 【{$attacker->getName()}】" + ); $attacker->addPhase(); $defender->addPhase(); - - if(!$attacker->continueWar($noRice)){ - //TODO: 퇴각해야함 + $attacker->logBattleResult(); + $defender->logBattleResult(); + $attacker->addLose(); $defender->addWin(); @@ -162,6 +175,9 @@ function processWar_NG( } if(!$defender->continueWar($noRice)){ + $attacker->logBattleResult(); + $defender->logBattleResult(); + $attacker->addWin(); $defender->addLose(); @@ -175,13 +191,16 @@ function processWar_NG( } $josaYi = JosaUtil::pick($defender->getCrewTypeName(), '이'); - $logger->pushGlobalActionLog("{$defender->getName()}의 {$defender->getCrewTypeName()}{$josaYi} 퇴각했습니다."); - $attacker->getLogger()->pushGeneralActionLog("{$defender->getName()}의 {$defender->getCrewTypeName()}{$josaYi} 퇴각했습니다.", ActionLogger::PLAIN); + if($noRice){ - $defender->getLogger()->pushGeneralActionLog("군량 부족으로 퇴각합니다.", ActionLogger::PLAIN); + $logger->pushGlobalActionLog("{$defender->getName()}의 {$defender->getCrewTypeName()}{$josaYi} 패퇴했습니다."); + $attacker->getLogger()->pushGeneralActionLog("{$defender->getName()}의 {$defender->getCrewTypeName()}{$josaYi} 패퇴했습니다.", ActionLogger::PLAIN); + $defender->getLogger()->pushGeneralActionLog("군량 부족으로 패퇴합니다.", ActionLogger::PLAIN); } else{ - $defender->getLogger()->pushGeneralActionLog("퇴각했습니다.", ActionLogger::PLAIN); + $logger->pushGlobalActionLog("{$defender->getName()}의 {$defender->getCrewTypeName()}{$josaYi} 전멸했습니다."); + $attacker->getLogger()->pushGeneralActionLog("{$defender->getName()}의 {$defender->getCrewTypeName()}{$josaYi} 전멸했습니다.", ActionLogger::PLAIN); + $defender->getLogger()->pushGeneralActionLog("전멸했습니다.", ActionLogger::PLAIN); } $defender->finishBattle(); @@ -194,6 +213,14 @@ function processWar_NG( } + if($currPhase == $maxPhase){ + $attacker->tryWound(); + $defender->tryWound(); + + $attacker->logBattleResult(); + $defender->logBattleResult(); + } + $attacker->finishBattle(); $defender->finishBattle(); diff --git a/hwe/sammo/ActionLogger.php b/hwe/sammo/ActionLogger.php index 905e445a..98fed4fa 100644 --- a/hwe/sammo/ActionLogger.php +++ b/hwe/sammo/ActionLogger.php @@ -143,7 +143,7 @@ class ActionLogger{ $this->generalBattleResultLog[] = $text; } - public function pushGeneralBattleDetailLog($text, int $formatType = self::RAWTEXT){ + public function pushGeneralBattleDetailLog($text, int $formatType = self::PLAIN){ if(!$text){ return; } @@ -243,4 +243,55 @@ class ActionLogger{ return $text; } + public function pushBattleResultTemplate( + WarUnit $me, + WarUnit $oppose + ){ + if($me instanceof WarUnitCity){ + return; + } + + $templates = new \League\Plates\Engine(__dir__.'/../templates'); + + $render_me = [ + 'crewtype' => $me->getCrewTypeShortName(), + 'name' => $me->getName(), + 'remain_crew' => $me->getHP(), + 'killed_crew' => $me->getDead() + ]; + + $render_oppose = [ + 'crewtype' => $oppose->getCrewTypeShortName(), + 'name' => $oppose->getName(), + 'remain_crew' => $oppose->getHP(), + 'killed_crew' => $oppose->getDead() + ]; + + if(!$me->isAttacker()){ + $warType = 'defense'; + $warTypeStr = '←'; + } + else if($oppose instanceof WarUnitCity){ + $warType = 'siege'; + $warTypeStr = '→'; + } + else{ + $warType = 'attack'; + $warTypeStr = '→'; + } + + $res = str_replace(["\r\n", "\r", "\n"], '', $templates->render('small_war_log',[ + 'year'=>$this->year, + 'month'=>$this->month, + 'war_type'=>$warType, + 'war_type_str'=>$warTypeStr, + 'me' => $render_me, + 'you' => $render_oppose, + ])); + + $this->pushGeneralBattleResultLog($res, self::EVENT_YEAR_MONTH); + $this->pushGeneralBattleDetailLog($res, self::EVENT_YEAR_MONTH); + $this->pushGeneralActionLog($res, self::EVENT_YEAR_MONTH); + } + } \ No newline at end of file diff --git a/hwe/sammo/GameUnitDetail.php b/hwe/sammo/GameUnitDetail.php index ada4b5e7..7761a54d 100644 --- a/hwe/sammo/GameUnitDetail.php +++ b/hwe/sammo/GameUnitDetail.php @@ -85,7 +85,7 @@ class GameUnitDetail{ public function getComputedAttack(array $general, int $tech){ if($this->armType == GameUnitConst::T_CASTLE){ assert(isset($general['def']) && isset($general['wall']), '도시 정보가 입력되어야 함'); - return ($general['def']*0.1 + $general['wall']*0.9) / 500 + 200; + return ($general['def'] + $general['wall']*9) / 500 + 200; } if($this->armType == GameUnitConst::T_WIZARD){ @@ -117,7 +117,7 @@ class GameUnitDetail{ public function getComputedDefence(array $general, int $tech){ if($this->armType == GameUnitConst::T_CASTLE){ assert(isset($general['def']) && isset($general['wall']), '도시 정보가 입력되어야 함'); - return ($general['def']*0.1 + $general['wall']*0.9) / 500 + 200; + return ($general['def'] + $general['wall']*9) / 500 + 200; } $def = $this->defence + getTechAbil($tech); $crew = ($general['crew'] / (7000 / 30)) + 70; diff --git a/hwe/sammo/WarUnit.php b/hwe/sammo/WarUnit.php index ee473506..a900a682 100644 --- a/hwe/sammo/WarUnit.php +++ b/hwe/sammo/WarUnit.php @@ -14,12 +14,12 @@ class WarUnit{ protected $updatedVar = []; - protected $genAtmos = 0; - protected $genTrain = 0; - protected $currPhase = 0; protected $prePhase = 0; + protected $atmosBonus = 0; + protected $trainBonus = 0; + protected $oppose; protected $warPower; protected $warPowerMultiply = 1.0; @@ -49,6 +49,10 @@ class WarUnit{ return 'EMPTY'; } + function isAttacker():bool{ + return $this->isAttacker; + } + function getCrewType():GameUnitDetail{ return $this->crewType; } @@ -184,10 +188,14 @@ class WarUnit{ return GameConst::$maxTrainByCommand; } - function getComputeAtmos(){ + function getComputedAtmos(){ return GameConst::$maxAtmosByCommand; } + function getComputedAvoidRatio(){ + return $this->getCrewType()->avoid / 100; + } + function addWin(){ throw new NotInheritedMethodException(); } @@ -278,6 +286,10 @@ class WarUnit{ return false; } + function logBattleResult(){ + $this->getLogger()->pushBattleResultTemplate($this, $this->getOppose()); + } + function applyDB($db):bool{ return false; } diff --git a/hwe/sammo/WarUnitCity.php b/hwe/sammo/WarUnitCity.php index 5a12bf2e..d0a593bf 100644 --- a/hwe/sammo/WarUnitCity.php +++ b/hwe/sammo/WarUnitCity.php @@ -8,7 +8,6 @@ class WarUnitCity extends WarUnit{ protected $crewType; protected $hp; - protected $trainAtmos; protected $rice = 0; public $cityRate; @@ -28,15 +27,22 @@ class WarUnitCity extends WarUnit{ $this->isAttacker = false; $this->cityRate = $cityRate; - $this->logger = new ActionLogger(0, $raw['nation'], $year, $month); + $this->logger = new ActionLogger(0, $raw['nation'], $year, $month, false); $this->crewType = GameUnitConst::byID($raw['crewtype']); $this->rice = $this->rawNation['rice']; $this->crewType = GameUnitConst::byID(GameUnitConst::T_CASTLE); - $this->hp = $this->raw['def'] * 10;; - $this->trainAtmos = $this->raw['wall'] * 10; + $this->hp = $this->raw['def'] * 10; + + //수비자 보정 + if($raw['level'] == 1){ + $this->trainBonus += 5; + } + else if($raw['level'] == 3){ + $this->trainBonus += 5; + } } function getRaw():array{ @@ -57,6 +63,14 @@ class WarUnitCity extends WarUnit{ return $this->killed; } + function getComputedTrain(){ + return $this->cityRate + $this->trainBonus; + } + + function getComputedAtmos(){ + return $this->cityRate + $this->atmosBonus; + } + function getHP():int{ return $this->hp; } @@ -65,7 +79,7 @@ class WarUnitCity extends WarUnit{ $damage = min($damage, $this->hp); $this->dead += $damage; $this->hp -= $damage; - $this->trainAtmos = max(0, $this->trainAtmos - $damage / 2); + $this->raw['wall'] = max(0, $this->raw['wall'] - $damage / 20); return $this->hp; } @@ -80,10 +94,25 @@ class WarUnitCity extends WarUnit{ return true; } + function addWin(){ + } + + function addLose(){ + } + + function heavyDecreseWealth(){ + $this->raw['agri'] *= 0.5; + $this->updatedVar['agri'] = true; + $this->raw['comm'] *= 0.5; + $this->updatedVar['comm'] = true; + $this->raw['secu'] *= 0.5; + $this->updatedVar['secu'] = true; + } + function finishBattle(){ $this->raw['def'] = Util::round($this->hp / 10); $this->updatedVar['def'] = true; - $this->raw['wall'] = Util::round($this->trainAtmos / 10); + Util::setRound($this->raw['wall']); $this->updatedVar['wall'] = true; //NOTE: 전투로 인한 사망자는 여기서 처리하지 않음 diff --git a/hwe/sammo/WarUnitGeneral.php b/hwe/sammo/WarUnitGeneral.php index 451ad8ad..288b4a33 100644 --- a/hwe/sammo/WarUnitGeneral.php +++ b/hwe/sammo/WarUnitGeneral.php @@ -13,11 +13,6 @@ class WarUnitGeneral extends WarUnit{ protected $updatedVar = []; - protected $genAtmos = 0; - protected $genTrain = 0; - protected $genAtmosBonus = 0; - protected $genTrainBonus = 0; - protected $sniped = false; @@ -35,19 +30,19 @@ class WarUnitGeneral extends WarUnit{ if($isAttacker){ //공격자 보정 if($rawCity['level'] == 2){ - $this->genAtmosBonus += 5; + $this->atmosBonus += 5; } if($rawNation['capital'] == $rawCity['city']){ - $this->genAtmosBonus += 5; + $this->atmosBonus += 5; } } else{ //수비자 보정 if($rawCity['level'] == 1){ - $this->genTrainBonus += 5; + $this->trainBonus += 5; } else if($rawCity['level'] == 3){ - $this->genTrainBonus += 5; + $this->trainBonus += 5; } } } @@ -96,6 +91,21 @@ class WarUnitGeneral extends WarUnit{ $this->updatedVar['atmos'] = true; } + function getComputedTrain(){ + $train = $this->raw['train']; + $train += $this->trainBonus; + + return $train; + } + + function getComputedAtmos(){ + return GameConst::$maxAtmosByCommand; + } + + function getComputedAvoidRatio(){ + $avoidRatio = $this->getCrewType()->avoid / 100; + } + function addWin(){ $this->win += 1; $this->raw['killnum'] += 1; @@ -233,34 +243,34 @@ class WarUnitGeneral extends WarUnit{ if($item == 3){ //탁주 사용 - $this->genAtmos += 3; + $this->addAtmos(3); $itemActivated = true; $itemConsumed = true; } else if($item >= 14 && $item <= 16){ //의적주, 두강주, 보령압주 사용 - $this->genAtmos += 5; + $this->addAtmos(5); $itemActivated = true; } else if($item >= 19 && $item <= 20){ //춘화첩, 초선화 사용 - $this->genAtmos += 7; + $this->addAtmos(7); $itemActivated = true; } else if($item == 4){ //청주 사용 - $this->genTrain += 3; + $this->addTrain(3); $itemActivated = true; $itemConsumed = true; } else if($item >= 12 && $item <= 13){ //과실주, 이강주 사용 - $this->genTrain += 5; + $this->addTrain(5); $itemActivated = true; } else if($item >= 18 && $item <= 18){ //철벽서, 단결도 사용 - $this->genTrain += 7; + $this->addTrain(7); $itemActivated = true; } @@ -340,7 +350,7 @@ class WarUnitGeneral extends WarUnit{ else if($armType == GameUnitConst::T_SIEGE) { $exp *= 0.9; } - $exp *= ($this->getComputedTrain() + $this->getComputeAtmos()) / 200; + $exp *= ($this->getComputedTrain() + $this->getComputedAtmos()) / 200; $ntype = $armType*10; $dexType = "dex{$ntype}"; diff --git a/hwe/templates/small_war_log.php b/hwe/templates/small_war_log.php index 634dff47..f7294dc7 100644 --- a/hwe/templates/small_war_log.php +++ b/hwe/templates/small_war_log.php @@ -1,9 +1,4 @@ -
년 - 월: - +