Add Chencang siege campaign chapter
This commit is contained in:
@@ -8,6 +8,7 @@ import fiftyThirdBattleMapUrl from '../../assets/images/battle/fifty-third-battl
|
||||
import fiftyFourthBattleMapUrl from '../../assets/images/battle/fifty-fourth-battle-map.svg';
|
||||
import fiftyFifthBattleMapUrl from '../../assets/images/battle/fifty-fifth-battle-map.svg';
|
||||
import fiftyEighthBattleMapUrl from '../../assets/images/battle/fifty-eighth-battle-map.svg';
|
||||
import fiftyNinthBattleMapUrl from '../../assets/images/battle/fifty-ninth-battle-map.svg';
|
||||
import fiftySeventhBattleMapUrl from '../../assets/images/battle/fifty-seventh-battle-map.svg';
|
||||
import fiftySixthBattleMapUrl from '../../assets/images/battle/fifty-sixth-battle-map.svg';
|
||||
import fifthBattleMapUrl from '../../assets/images/battle/fifth-battle-map.svg';
|
||||
@@ -114,6 +115,7 @@ export const battleMapAssets: Record<string, string> = {
|
||||
'battle-map-fifty-fourth': fiftyFourthBattleMapUrl,
|
||||
'battle-map-fifty-fifth': fiftyFifthBattleMapUrl,
|
||||
'battle-map-fifty-eighth': fiftyEighthBattleMapUrl,
|
||||
'battle-map-fifty-ninth': fiftyNinthBattleMapUrl,
|
||||
'battle-map-fifty-seventh': fiftySeventhBattleMapUrl,
|
||||
'battle-map-fifty-sixth': fiftySixthBattleMapUrl
|
||||
};
|
||||
|
||||
@@ -31,6 +31,10 @@ import {
|
||||
fiftySixthBattleMap,
|
||||
fiftySixthBattleUnits,
|
||||
fiftySixthBattleVictoryPages,
|
||||
fiftyNinthBattleBonds,
|
||||
fiftyNinthBattleMap,
|
||||
fiftyNinthBattleUnits,
|
||||
fiftyNinthBattleVictoryPages,
|
||||
fiftySeventhBattleBonds,
|
||||
fiftySeventhBattleMap,
|
||||
fiftySeventhBattleUnits,
|
||||
@@ -295,7 +299,8 @@ export type BattleScenarioId =
|
||||
| 'fifty-fifth-battle-northern-qishan-road'
|
||||
| 'fifty-sixth-battle-tianshui-advance'
|
||||
| 'fifty-seventh-battle-jieting-crisis'
|
||||
| 'fifty-eighth-battle-qishan-retreat';
|
||||
| 'fifty-eighth-battle-qishan-retreat'
|
||||
| 'fifty-ninth-battle-chencang-siege';
|
||||
|
||||
export type BattleObjectiveKind = 'defeat-leader' | 'pacify-leader' | 'keep-unit-alive' | 'secure-terrain' | 'quick-victory';
|
||||
|
||||
@@ -3861,6 +3866,87 @@ export const fiftyEighthBattleScenario: BattleScenarioDefinition = {
|
||||
nextCampScene: 'CampScene'
|
||||
};
|
||||
|
||||
export const fiftyNinthBattleScenario: BattleScenarioDefinition = {
|
||||
id: 'fifty-ninth-battle-chencang-siege',
|
||||
title: '진창 공성전',
|
||||
victoryConditionLabel: '학소 진창 수비 압박과 왕쌍 추격 차단',
|
||||
defeatConditionLabel: '제갈량 퇴각 또는 공성 진영 붕괴',
|
||||
openingObjectiveLines: [
|
||||
'기산에서 후퇴한 뒤 촉한군은 병사와 장부를 다시 묶어 진창 성채를 압박합니다. 학소가 성벽을 굳게 지키고 있어 성문 하나만 바라보는 공격은 오래 버티지 못합니다.',
|
||||
'강유는 길을 알고, 왕평은 진영 표식을 보며, 위연은 돌파를 원합니다. 여기에 황권과 마량, 법정의 장부와 계책을 어떻게 넣을지에 따라 공성전의 무게가 달라집니다.',
|
||||
'학소의 수비를 흔들고 왕쌍의 추격을 차단하십시오. 공성 진영과 군량 수레 길을 함께 지키면 다음 북방 계산으로 이어갈 수 있습니다.'
|
||||
],
|
||||
map: fiftyNinthBattleMap,
|
||||
units: fiftyNinthBattleUnits,
|
||||
bonds: fiftyNinthBattleBonds,
|
||||
mapTextureKey: 'battle-map-fifty-ninth',
|
||||
leaderUnitId: 'northern-fifth-leader-hao-zhao',
|
||||
quickVictoryTurnLimit: 118,
|
||||
baseVictoryGold: 17280,
|
||||
objectives: [
|
||||
{
|
||||
id: 'pressure-hao-zhao',
|
||||
kind: 'defeat-leader',
|
||||
label: '학소 진창 수비 압박',
|
||||
rewardGold: 12040,
|
||||
unitId: 'northern-fifth-leader-hao-zhao'
|
||||
},
|
||||
{
|
||||
id: 'halt-wang-shuang',
|
||||
kind: 'defeat-leader',
|
||||
label: '왕쌍 추격 차단',
|
||||
rewardGold: 6000,
|
||||
unitId: 'northern-fifth-officer-wang-shuang'
|
||||
},
|
||||
{
|
||||
id: 'zhuge-liang',
|
||||
kind: 'keep-unit-alive',
|
||||
label: '제갈량 생존',
|
||||
rewardGold: 3100,
|
||||
unitId: 'zhuge-liang'
|
||||
},
|
||||
{
|
||||
id: 'chencang-gate',
|
||||
kind: 'secure-terrain',
|
||||
label: '진창 성문 압박',
|
||||
rewardGold: 6200,
|
||||
terrain: 'fort'
|
||||
},
|
||||
{
|
||||
id: 'siege-camps',
|
||||
kind: 'secure-terrain',
|
||||
label: '공성 진영 유지',
|
||||
rewardGold: 5940,
|
||||
terrain: 'camp'
|
||||
},
|
||||
{
|
||||
id: 'grain-road',
|
||||
kind: 'secure-terrain',
|
||||
label: '군량 수레 길 확보',
|
||||
rewardGold: 5820,
|
||||
terrain: 'road'
|
||||
},
|
||||
{
|
||||
id: 'rear-villages',
|
||||
kind: 'secure-terrain',
|
||||
label: '후방 마을 안정',
|
||||
rewardGold: 5480,
|
||||
terrain: 'village'
|
||||
},
|
||||
{
|
||||
id: 'quick',
|
||||
kind: 'quick-victory',
|
||||
label: '118턴 이내 진창 압박 완료',
|
||||
rewardGold: 3840,
|
||||
maxTurn: 118
|
||||
}
|
||||
],
|
||||
defeatConditions: [{ kind: 'unit-defeated', unitId: 'zhuge-liang' }],
|
||||
itemRewards: ['금 104', '상처약 86', '군주 42', '진창 공성 장부 1', '왕쌍 추격 기록 1'],
|
||||
victoryPages: fiftyNinthBattleVictoryPages,
|
||||
nextCampScene: 'CampScene'
|
||||
};
|
||||
|
||||
export const defaultBattleScenarioId: BattleScenarioId = firstBattleScenario.id;
|
||||
|
||||
export const battleScenarios: Record<BattleScenarioId, BattleScenarioDefinition> = {
|
||||
@@ -3921,7 +4007,8 @@ export const battleScenarios: Record<BattleScenarioId, BattleScenarioDefinition>
|
||||
'fifty-fifth-battle-northern-qishan-road': fiftyFifthBattleScenario,
|
||||
'fifty-sixth-battle-tianshui-advance': fiftySixthBattleScenario,
|
||||
'fifty-seventh-battle-jieting-crisis': fiftySeventhBattleScenario,
|
||||
'fifty-eighth-battle-qishan-retreat': fiftyEighthBattleScenario
|
||||
'fifty-eighth-battle-qishan-retreat': fiftyEighthBattleScenario,
|
||||
'fifty-ninth-battle-chencang-siege': fiftyNinthBattleScenario
|
||||
};
|
||||
|
||||
export const defaultBattleScenario = battleScenarios[defaultBattleScenarioId];
|
||||
|
||||
@@ -12,6 +12,7 @@ import {
|
||||
fiftyFourthBattleScenario,
|
||||
fiftyFifthBattleScenario,
|
||||
fiftySixthBattleScenario,
|
||||
fiftyNinthBattleScenario,
|
||||
fiftySeventhBattleScenario,
|
||||
fortiethBattleScenario,
|
||||
fortyFirstBattleScenario,
|
||||
@@ -72,6 +73,8 @@ import {
|
||||
fiftiethBattleVictoryPages,
|
||||
fiftyEighthBattleIntroPages,
|
||||
fiftyEighthBattleVictoryPages,
|
||||
fiftyNinthBattleIntroPages,
|
||||
fiftyNinthBattleVictoryPages,
|
||||
fiftyFirstBattleIntroPages,
|
||||
fiftyFirstBattleVictoryPages,
|
||||
fiftySecondBattleIntroPages,
|
||||
@@ -855,13 +858,24 @@ const sortieFlows: Record<string, SortieFlow> = {
|
||||
},
|
||||
[fiftyEighthBattleScenario.id]: {
|
||||
afterBattleId: fiftyEighthBattleScenario.id,
|
||||
eyebrow: '다음 장 준비',
|
||||
title: '기산 후퇴로 이후',
|
||||
eyebrow: '다음 전장',
|
||||
title: fiftyNinthBattleScenario.title,
|
||||
description:
|
||||
'기산 후퇴로에서 병사와 장부를 지켜 냈습니다. 그러나 이것은 북벌의 끝이 아니라 다음 출정을 위한 정비입니다. 강유의 첫 출전, 왕평의 물길 판단, 조운과 마대의 귀환선을 군영에서 다시 정리합니다.',
|
||||
rewardHint: '다음 목표: 북벌 재정비 / 강유 첫 출전 평가',
|
||||
pages: fiftyEighthBattleVictoryPages,
|
||||
unavailableNotice: '기산 후퇴로 이후의 다음 북벌 전투는 이어지는 작업에서 확장합니다. 현재는 강유 첫 출전 후 군영 대화, 보급 정비, 출전 편성 방향을 확인할 수 있습니다.'
|
||||
'기산 후퇴로에서 병사와 장부를 지켜 냈습니다. 이제 다시 북쪽을 보되, 진창 성채의 학소와 왕쌍의 추격을 상대해야 합니다. 강유의 길 판단과 공성 진영, 군량 수레를 함께 계산하십시오.',
|
||||
rewardHint: `예상 보상: ${fiftyNinthBattleScenario.title} 개방 / 진창 공성 장부`,
|
||||
nextBattleId: fiftyNinthBattleScenario.id,
|
||||
campaignStep: 'fifty-ninth-battle',
|
||||
pages: [...fiftyEighthBattleVictoryPages, ...fiftyNinthBattleIntroPages]
|
||||
},
|
||||
[fiftyNinthBattleScenario.id]: {
|
||||
afterBattleId: fiftyNinthBattleScenario.id,
|
||||
eyebrow: '다음 장 준비',
|
||||
title: '진창 공성전 이후',
|
||||
description:
|
||||
'진창 성채를 압박하고 왕쌍의 추격을 끊었지만, 성을 오래 물고 늘어지는 북벌은 군량의 시간을 갉아먹습니다. 이것은 결말이 아니라 다음 북방 계산을 위한 경계선입니다.',
|
||||
rewardHint: '다음 목표: 북벌 보급 재계산 / 진창 공성 평가',
|
||||
pages: fiftyNinthBattleVictoryPages,
|
||||
unavailableNotice: '진창 공성전 이후의 다음 북벌 전투는 이어지는 작업에서 확장합니다. 현재는 진창 공성 평가, 보급 재계산, 강유와 위연의 편성 방향을 확인할 수 있습니다.'
|
||||
},
|
||||
'northern-campaign-prep-camp-legacy': {
|
||||
afterBattleId: fiftyFourthBattleScenario.id,
|
||||
|
||||
@@ -3748,6 +3748,59 @@ export const fiftyEighthBattleVictoryPages: StoryPage[] = [
|
||||
}
|
||||
];
|
||||
|
||||
export const fiftyNinthBattleIntroPages: StoryPage[] = [
|
||||
{
|
||||
id: 'fifty-ninth-chencang-order',
|
||||
bgm: 'story-dark',
|
||||
chapter: '진창 성채',
|
||||
background: 'story-militia',
|
||||
speaker: '제갈량',
|
||||
text: '기산에서 병사를 살렸기에 다시 북쪽을 볼 수 있습니다. 그러나 이번 길은 넓은 들이 아니라 진창의 굳은 성채입니다. 성문을 무리하게 깨기보다 공성 진영, 군량 수레, 퇴로를 함께 보아야 합니다.'
|
||||
},
|
||||
{
|
||||
id: 'fifty-ninth-hao-zhao-wall',
|
||||
bgm: 'battle-prep',
|
||||
chapter: '학소의 성벽',
|
||||
background: 'story-sortie',
|
||||
speaker: '강유',
|
||||
text: '진창의 수비장 학소는 성을 버리지 않을 사람입니다. 제가 앞길을 살피겠습니다만, 성벽만 바라보면 왕쌍의 기병이 뒤를 물 것입니다. 조운, 마대, 왕평 중 누구를 앞으로 세우느냐가 이번 편성의 무게입니다.'
|
||||
},
|
||||
{
|
||||
id: 'fifty-ninth-supply-limit',
|
||||
bgm: 'story-dark',
|
||||
chapter: '군량의 시간',
|
||||
background: 'story-three-heroes',
|
||||
speaker: '황권',
|
||||
text: '성채 하나에 오래 묶이면 북벌 전체가 굶습니다. 법정의 계책, 마량의 문서, 황권의 장부가 함께 있어야 공성전이 단순한 힘겨루기로 흐르지 않습니다. 진창을 압박하되 돌아갈 수 있는 시간을 남기십시오.'
|
||||
}
|
||||
];
|
||||
|
||||
export const fiftyNinthBattleVictoryPages: StoryPage[] = [
|
||||
{
|
||||
id: 'fifty-ninth-victory-chencang-pressure',
|
||||
bgm: 'militia-theme',
|
||||
chapter: '진창 압박',
|
||||
background: 'story-sortie',
|
||||
text: '촉한군은 진창의 외곽 진영과 보급로를 흔들었지만, 학소의 성벽은 끝내 쉽게 열리지 않았습니다. 승리라 부르기에는 조심스럽고 패배라 덮기에는 얻은 길이 분명한 전투였습니다.'
|
||||
},
|
||||
{
|
||||
id: 'fifty-ninth-victory-wang-shuang-cut',
|
||||
bgm: 'story-dark',
|
||||
chapter: '왕쌍 추격 차단',
|
||||
background: 'story-militia',
|
||||
speaker: '조운',
|
||||
text: '왕쌍의 기병은 공성 진영 뒤를 물려 했으나, 강유의 길 안내와 마대의 우회, 왕평의 진영 표식이 먼저 움직였습니다. 오래 버티는 성을 상대로도 물러날 때를 정하는 장수가 필요합니다.'
|
||||
},
|
||||
{
|
||||
id: 'fifty-ninth-next-northern-plan',
|
||||
bgm: 'story-dark',
|
||||
chapter: '다음 북방 계산',
|
||||
background: 'story-three-heroes',
|
||||
speaker: '제갈량',
|
||||
text: '진창은 북벌의 끝이 아니라, 무리한 공세가 어디서 멈춰야 하는지를 보여 준 성입니다. 다음 출정에서는 성을 치는 힘뿐 아니라 군량이 버틸 날, 돌아올 길, 장수의 고집을 모두 함께 계산해야 합니다.'
|
||||
}
|
||||
];
|
||||
|
||||
export const firstBattleMap: BattleMap = {
|
||||
width: 20,
|
||||
height: 18,
|
||||
@@ -4241,6 +4294,12 @@ export const fiftyEighthBattleMap: BattleMap = {
|
||||
terrain: createFiftyEighthBattleTerrain()
|
||||
};
|
||||
|
||||
export const fiftyNinthBattleMap: BattleMap = {
|
||||
width: 118,
|
||||
height: 100,
|
||||
terrain: createFiftyNinthBattleTerrain()
|
||||
};
|
||||
|
||||
export const firstBattleUnits: UnitData[] = [
|
||||
{
|
||||
id: 'liu-bei',
|
||||
@@ -17276,6 +17335,97 @@ export const fiftyEighthBattleUnits: UnitData[] = [
|
||||
createThirtyFirstEnemyUnit('northern-fourth-leader-sima-yi', '사마의', '위군 본대 총지휘관', 'rebelLeader', 193, 1500, 352, 112, 27)
|
||||
];
|
||||
|
||||
const fiftyNinthBattleAllyPositions: Record<string, { x: number; y: number }> = {
|
||||
'guan-yu': { x: 18, y: 88 },
|
||||
'zhang-fei': { x: 24, y: 90 },
|
||||
'jian-yong': { x: 10, y: 95 },
|
||||
'mi-zhu': { x: 14, y: 96 },
|
||||
'sun-qian': { x: 19, y: 96 },
|
||||
'zhao-yun': { x: 31, y: 86 },
|
||||
'zhuge-liang': { x: 17, y: 85 },
|
||||
'ma-liang': { x: 22, y: 82 },
|
||||
'yi-ji': { x: 9, y: 98 },
|
||||
'gong-zhi': { x: 27, y: 96 },
|
||||
'huang-zhong': { x: 37, y: 84 },
|
||||
'wei-yan': { x: 43, y: 86 },
|
||||
'pang-tong': { x: 15, y: 81 },
|
||||
'fa-zheng': { x: 27, y: 80 },
|
||||
'wu-yi': { x: 45, y: 94 },
|
||||
'yan-yan': { x: 49, y: 87 },
|
||||
'li-yan': { x: 35, y: 79 },
|
||||
'huang-quan': { x: 12, y: 84 },
|
||||
'ma-chao': { x: 52, y: 83 },
|
||||
'ma-dai': { x: 56, y: 90 },
|
||||
'wang-ping': { x: 40, y: 79 },
|
||||
'jiang-wei': { x: 33, y: 82 }
|
||||
};
|
||||
|
||||
export const fiftyNinthBattleUnits: UnitData[] = [
|
||||
...[
|
||||
...firstBattleUnits.filter((unit) => unit.faction === 'ally' && unit.id !== 'liu-bei'),
|
||||
...xuzhouRecruitUnits,
|
||||
...caoBreakRecruitUnits,
|
||||
...liuBiaoRecruitUnits,
|
||||
...zhugeRecruitUnits,
|
||||
...jingzhouRecruitUnits,
|
||||
...guiyangRecruitUnits,
|
||||
...wulingRecruitUnits,
|
||||
...changshaRecruitUnits,
|
||||
...yizhouRecruitUnits,
|
||||
...fuPassRecruitUnits,
|
||||
...luoCastleRecruitUnits,
|
||||
...luoCastleProperRecruitUnits,
|
||||
...chengduPressureRecruitUnits,
|
||||
...chengduSurrenderRecruitUnits,
|
||||
...hanzhongOpeningRecruitUnits,
|
||||
...hanzhongScoutRecruitUnits,
|
||||
...hanzhongMainRecruitUnits,
|
||||
...jiangWeiRecruitUnits
|
||||
].map((unit) => placeScenarioUnit(unit, fiftyNinthBattleAllyPositions[unit.id] ?? { x: unit.x, y: unit.y })),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-scout-a', '진창 외곽 척후병', '서쪽 수레길 정찰', 'bandit', 190, 960, 270, 49, 78),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-scout-b', '진창 외곽 척후병', '공성 진영 정찰', 'bandit', 190, 960, 270, 60, 74),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-scout-c', '진창 외곽 척후병', '중앙 낮은 길 정찰', 'bandit', 191, 972, 272, 72, 67),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-scout-d', '진창 외곽 척후병', '동쪽 성문 정찰', 'bandit', 191, 972, 272, 84, 60),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-scout-e', '진창 외곽 척후병', '학소 성벽 정찰', 'bandit', 192, 984, 274, 101, 42),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-scout-f', '진창 외곽 척후병', '북쪽 봉화 정찰', 'bandit', 192, 984, 274, 114, 25),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-infantry-a', '위군 진창 보병', '서쪽 공성로 보병', 'yellowTurban', 191, 1340, 324, 54, 73),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-infantry-b', '위군 진창 보병', '수레길 보병', 'yellowTurban', 191, 1340, 324, 64, 68),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-infantry-c', '위군 진창 보병', '중앙 보병', 'yellowTurban', 192, 1360, 328, 76, 62),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-infantry-d', '위군 진창 보병', '동문 앞 보병', 'yellowTurban', 192, 1360, 328, 88, 55),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-infantry-e', '위군 진창 보병', '성벽 아래 보병', 'yellowTurban', 193, 1380, 332, 100, 48),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-infantry-f', '위군 진창 보병', '학소 본영 보병', 'yellowTurban', 193, 1380, 332, 110, 36),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-infantry-g', '위군 진창 보병', '보급 차단 보병', 'yellowTurban', 194, 1400, 336, 92, 76),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-infantry-h', '위군 진창 보병', '북쪽 성벽 보병', 'yellowTurban', 194, 1400, 336, 115, 18),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-archer-a', '진창 성벽 궁병', '서쪽 성벽 궁병', 'archer', 191, 1010, 282, 60, 63),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-archer-b', '진창 성벽 궁병', '공성로 궁병', 'archer', 191, 1010, 282, 71, 58),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-archer-c', '진창 성벽 궁병', '중앙 성벽 궁병', 'archer', 192, 1022, 284, 84, 51),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-archer-d', '진창 성벽 궁병', '동문 궁병', 'archer', 193, 1034, 286, 96, 44),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-archer-e', '진창 성벽 궁병', '학소 본영 궁병', 'archer', 193, 1034, 286, 108, 31),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-archer-f', '진창 성벽 궁병', '봉화대 궁병', 'archer', 194, 1046, 288, 116, 16),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-cavalry-a', '왕쌍 추격 기병', '서쪽 추격 기병', 'cavalry', 192, 1388, 338, 50, 66),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-cavalry-b', '왕쌍 추격 기병', '수레길 추격 기병', 'cavalry', 192, 1388, 338, 63, 63),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-cavalry-c', '왕쌍 추격 기병', '중앙 돌파 기병', 'cavalry', 193, 1410, 342, 77, 56),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-cavalry-d', '왕쌍 추격 기병', '동쪽 우회 기병', 'cavalry', 194, 1432, 346, 91, 49),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-cavalry-e', '왕쌍 추격 기병', '성문 지원 기병', 'cavalry', 194, 1432, 346, 103, 41),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-cavalry-f', '왕쌍 추격 기병', '북쪽 추격 기병', 'cavalry', 195, 1454, 350, 114, 27),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-wall-guard-a', '진창 성벽 수비대', '서쪽 성벽 수비', 'yellowTurban', 192, 1360, 330, 44, 53),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-wall-guard-b', '진창 성벽 수비대', '중앙 성벽 수비', 'yellowTurban', 192, 1360, 330, 58, 47),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-wall-guard-c', '진창 성벽 수비대', '동문 수비', 'yellowTurban', 193, 1380, 334, 74, 39),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-wall-guard-d', '진창 성벽 수비대', '내성 수비', 'yellowTurban', 193, 1380, 334, 90, 32),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-wall-guard-e', '진창 성벽 수비대', '학소 본영 수비', 'yellowTurban', 194, 1400, 338, 104, 24),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-wall-guard-f', '진창 성벽 수비대', '북쪽 절벽 수비', 'yellowTurban', 194, 1400, 338, 116, 13),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-strategist-a', '위군 공성 대응 군리', '성벽 수리 군리', 'strategist', 192, 1080, 296, 72, 54),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-strategist-b', '위군 공성 대응 군리', '봉화 연락 군리', 'strategist', 193, 1092, 298, 86, 45),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-strategist-c', '위군 공성 대응 군리', '학소 본영 군리', 'strategist', 193, 1092, 298, 100, 36),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-strategist-d', '위군 공성 대응 군리', '군량 차단 군리', 'strategist', 194, 1104, 300, 106, 63),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-officer-wang-shuang', '왕쌍', '위군 추격 장수', 'rebelLeader', 196, 1480, 356, 87, 72),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-officer-fei-yao', '비요', '진창 지원 장수', 'rebelLeader', 194, 1440, 348, 101, 58),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-officer-guo-huai', '곽회', '북방 지원 장수', 'rebelLeader', 194, 1440, 348, 110, 68),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-officer-supply', '위군 군량 차단장', '공성 진영 압박 장수', 'rebelLeader', 193, 1420, 344, 78, 76),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-officer-wall', '진창 성벽 장수', '성문 수비 장수', 'rebelLeader', 194, 1440, 348, 112, 27),
|
||||
createThirtyFirstEnemyUnit('northern-fifth-leader-hao-zhao', '학소', '진창 수비장', 'rebelLeader', 197, 1540, 362, 109, 35)
|
||||
];
|
||||
|
||||
export const firstBattleBonds: BattleBond[] = [
|
||||
{
|
||||
id: 'liu-bei__guan-yu',
|
||||
@@ -18513,6 +18663,46 @@ export const fiftyEighthBattleBonds: BattleBond[] = [
|
||||
...northernFourthBattleBonds
|
||||
].map(cloneBattleBondForScenario);
|
||||
|
||||
export const northernFifthBattleBonds: BattleBond[] = [
|
||||
{
|
||||
id: 'jiang-wei__fa-zheng_northern-fifth',
|
||||
unitIds: ['jiang-wei', 'fa-zheng'],
|
||||
title: '새 길과 오래된 계책',
|
||||
level: 46,
|
||||
exp: 0,
|
||||
description: '강유의 진창 길 판단과 법정의 공성 계책이 맞물리면 성벽을 무리하게 치기보다 수비의 빈틈을 재는 힘이 생깁니다.'
|
||||
},
|
||||
{
|
||||
id: 'wei-yan__jiang-wei_northern-fifth',
|
||||
unitIds: ['wei-yan', 'jiang-wei'],
|
||||
title: '돌파와 절제',
|
||||
level: 42,
|
||||
exp: 0,
|
||||
description: '위연의 돌파 욕심과 강유의 길 계산을 함께 묶으면 성채 앞에서 밀어붙일 곳과 멈출 곳을 구분할 수 있습니다.'
|
||||
},
|
||||
{
|
||||
id: 'huang-quan__ma-liang_northern-fifth',
|
||||
unitIds: ['huang-quan', 'ma-liang'],
|
||||
title: '군량과 문서',
|
||||
level: 52,
|
||||
exp: 0,
|
||||
description: '황권의 군량 장부와 마량의 명분 문서가 함께 움직이면 진창 공성전이 오래 끌릴 때도 후방의 약속이 흔들리지 않습니다.'
|
||||
},
|
||||
{
|
||||
id: 'wang-ping__ma-dai_northern-fifth',
|
||||
unitIds: ['wang-ping', 'ma-dai'],
|
||||
title: '진영 표식과 우회 기병',
|
||||
level: 44,
|
||||
exp: 0,
|
||||
description: '왕평의 진영 표식과 마대의 우회 기병이 어울리면 왕쌍의 추격을 받기 전에 공성 진영을 접을 시간을 벌 수 있습니다.'
|
||||
}
|
||||
];
|
||||
|
||||
export const fiftyNinthBattleBonds: BattleBond[] = [
|
||||
...fiftyEighthBattleBonds,
|
||||
...northernFifthBattleBonds
|
||||
].map(cloneBattleBondForScenario);
|
||||
|
||||
function createEighthBattleTerrain(): TerrainType[][] {
|
||||
return Array.from({ length: 22 }, (_, y) =>
|
||||
Array.from({ length: 26 }, (_, x): TerrainType => {
|
||||
@@ -21681,6 +21871,81 @@ function createFiftyEighthBattleTerrain(): TerrainType[][] {
|
||||
);
|
||||
}
|
||||
|
||||
function createFiftyNinthBattleTerrain(): TerrainType[][] {
|
||||
return Array.from({ length: 100 }, (_, y) =>
|
||||
Array.from({ length: 118 }, (_, x): TerrainType => {
|
||||
if (
|
||||
(x >= 4 && x <= 10 && y >= 0 && y <= 99) ||
|
||||
(x >= 60 && x <= 67 && y >= 20 && y <= 99) ||
|
||||
(x >= 0 && x <= 117 && y >= 92)
|
||||
) {
|
||||
return 'river';
|
||||
}
|
||||
if (
|
||||
(x >= 10 && x <= 78 && y >= 84 && y <= 90) ||
|
||||
(x >= 24 && x <= 94 && y >= 72 && y <= 80) ||
|
||||
(x >= 48 && x <= 106 && y >= 60 && y <= 70) ||
|
||||
(x >= 72 && x <= 114 && y >= 47 && y <= 58) ||
|
||||
(x >= 92 && x <= 117 && y >= 33 && y <= 44) ||
|
||||
(x >= 30 && x <= 38 && y >= 66 && y <= 94) ||
|
||||
(x >= 54 && x <= 62 && y >= 54 && y <= 86) ||
|
||||
(x >= 84 && x <= 92 && y >= 39 && y <= 76)
|
||||
) {
|
||||
return 'road';
|
||||
}
|
||||
if (
|
||||
(x >= 0 && x <= 34 && y >= 56 && y <= 88) ||
|
||||
(x >= 42 && x <= 76 && y >= 70 && y <= 91) ||
|
||||
(x >= 88 && x <= 117 && y >= 63 && y <= 88) ||
|
||||
(x >= 14 && x <= 36 && y >= 40 && y <= 58)
|
||||
) {
|
||||
return 'forest';
|
||||
}
|
||||
if (
|
||||
(x >= 0 && x <= 48 && y <= 36) ||
|
||||
(x >= 46 && x <= 88 && y <= 30) ||
|
||||
(x >= 86 && x <= 117 && y <= 48) ||
|
||||
(x >= 98 && x <= 117 && y >= 42 && y <= 68)
|
||||
) {
|
||||
return 'hill';
|
||||
}
|
||||
if (
|
||||
(x <= 2 && y <= 90) ||
|
||||
(x >= 115 && y <= 84) ||
|
||||
(x >= 37 && x <= 43 && y >= 0 && y <= 60) ||
|
||||
(x >= 74 && x <= 80 && y >= 0 && y <= 42) ||
|
||||
(x >= 58 && x <= 65 && y >= 82 && y <= 99)
|
||||
) {
|
||||
return 'cliff';
|
||||
}
|
||||
if (
|
||||
(x >= 12 && x <= 27 && y >= 80 && y <= 90) ||
|
||||
(x >= 44 && x <= 61 && y >= 68 && y <= 79) ||
|
||||
(x >= 77 && x <= 94 && y >= 54 && y <= 66) ||
|
||||
(x >= 98 && x <= 114 && y >= 39 && y <= 52)
|
||||
) {
|
||||
return 'village';
|
||||
}
|
||||
if (
|
||||
(x >= 20 && x <= 44 && y >= 75 && y <= 88) ||
|
||||
(x >= 54 && x <= 78 && y >= 62 && y <= 74) ||
|
||||
(x >= 86 && x <= 108 && y >= 48 && y <= 61)
|
||||
) {
|
||||
return 'camp';
|
||||
}
|
||||
if (
|
||||
(x >= 48 && x <= 66 && y >= 43 && y <= 58) ||
|
||||
(x >= 72 && x <= 94 && y >= 33 && y <= 48) ||
|
||||
(x >= 92 && x <= 114 && y >= 42 && y <= 58) ||
|
||||
(x >= 100 && x <= 117 && y >= 12 && y <= 31)
|
||||
) {
|
||||
return 'fort';
|
||||
}
|
||||
return 'plain';
|
||||
})
|
||||
);
|
||||
}
|
||||
|
||||
function placeScenarioUnit(unit: UnitData, position: { x: number; y: number }): UnitData {
|
||||
return {
|
||||
...cloneUnitForScenario(unit),
|
||||
|
||||
Reference in New Issue
Block a user