merge: 전투 통계 행 정렬을 main에 반영한다

This commit is contained in:
2026-08-21 16:48:25 +00:00
3 changed files with 55 additions and 35 deletions
+24 -26
View File
@@ -38,6 +38,18 @@ const readGeneralPanelImages = async (panel: Locator) =>
}) })
); );
const readGeneralSummaryRows = async (summary: Locator) =>
summary.evaluate((element) => {
const rows = new Map<number, string[]>();
for (const label of element.querySelectorAll<HTMLElement>(':scope > span')) {
const top = Math.round(label.getBoundingClientRect().top * 100) / 100;
const row = rows.get(top) ?? [];
row.push(label.textContent?.trim() ?? '');
rows.set(top, row);
}
return [...rows.values()];
});
type FixtureState = { type FixtureState = {
permission: 'head' | 'member'; permission: 'head' | 'member';
myset: number; myset: number;
@@ -1242,19 +1254,12 @@ test('내 정보&설정 keeps desktop density and becomes a 390px horizontal-ide
await expect(page.locator('.battle-general-extra')).toContainText('피살6,789'); await expect(page.locator('.battle-general-extra')).toContainText('피살6,789');
await expect(page.locator('.battle-general-extra__recent-value')).toHaveText('01-01 00:00'); await expect(page.locator('.battle-general-extra__recent-value')).toHaveText('01-01 00:00');
await expect(page.locator('.legacy-general-details')).toHaveCount(0); await expect(page.locator('.legacy-general-details')).toHaveCount(0);
await expect(page.locator('.battle-general-extra > span')).toHaveText([ expect(await readGeneralSummaryRows(page.locator('.battle-general-extra'))).toEqual([
'명성', ['명성', '계급', ''],
'계', ['전투', '계', '사관'],
'전투', ['승률', '승리', '패배'],
'승리', ['살상률', '사살', '피살'],
'패배', ['최근 전투'],
'계략',
'사관',
'사살',
'피살',
'승률',
'살상률',
'최근 전투',
]); ]);
await expect(page.locator('.item-group')).toContainText('명마'); await expect(page.locator('.item-group')).toContainText('명마');
await expect(page.locator('#container')).not.toContainText('che_'); await expect(page.locator('#container')).not.toContainText('che_');
@@ -2043,19 +2048,12 @@ test('감찰부 keeps the selector interaction and shows the permission error pa
await expect(page.locator('.battle-general-extra')).toContainText('사관4년'); await expect(page.locator('.battle-general-extra')).toContainText('사관4년');
await expect(page.locator('.battle-general-extra')).toContainText('승률62.50%'); await expect(page.locator('.battle-general-extra')).toContainText('승률62.50%');
await expect(page.locator('.battle-general-extra')).toContainText('살상률181.84%'); await expect(page.locator('.battle-general-extra')).toContainText('살상률181.84%');
await expect(page.locator('.battle-general-extra > span')).toHaveText([ expect(await readGeneralSummaryRows(page.locator('.battle-general-extra'))).toEqual([
'명성', ['명성', '계급', ''],
'계', ['전투', '계', '사관'],
'전투', ['승률', '승리', '패배'],
'승리', ['살상률', '사살', '피살'],
'패배', ['최근 전투'],
'계략',
'사관',
'사살',
'피살',
'승률',
'살상률',
'최근 전투',
]); ]);
const battleImages = await readGeneralPanelImages(page.locator('.battle-general-card')); const battleImages = await readGeneralPanelImages(page.locator('.battle-general-card'));
expect(battleImages).toHaveLength(2); expect(battleImages).toHaveLength(2);
+2 -2
View File
@@ -278,8 +278,8 @@ test('past plays is available without a current general and preserves desktop in
await expect(detailToggle).toHaveAttribute('aria-expanded', 'true'); await expect(detailToggle).toHaveAttribute('aria-expanded', 'true');
await expect(page.locator('.archive-general-card')).toHaveAttribute('data-general-basic-card', ''); await expect(page.locator('.archive-general-card')).toHaveAttribute('data-general-basic-card', '');
await expect(page.locator('.archive-general-card [role="progressbar"]')).toHaveCount(14); await expect(page.locator('.archive-general-card [role="progressbar"]')).toHaveCount(14);
await expect(page.locator('[data-general-battle-summary]')).toContainText('승률62.5%'); await expect(page.locator('[data-general-battle-summary]')).toContainText('승률62.50%');
await expect(page.locator('[data-general-battle-summary]')).toContainText('살상률75.0%'); await expect(page.locator('[data-general-battle-summary]')).toContainText('살상률75.00%');
const hallBattle = page.locator('[data-hall-battle-record]'); const hallBattle = page.locator('[data-hall-battle-record]');
await expect(hallBattle).toContainText('명예의 전당 보존 기록'); await expect(hallBattle).toContainText('명예의 전당 보존 기록');
await expect(hallBattle).toContainText('항목별 기록 시점이 서로 다를 수 있습니다.'); await expect(hallBattle).toContainText('항목별 기록 시점이 서로 다를 수 있습니다.');
@@ -61,11 +61,12 @@ const killRate = computed(() => {
</div> </div>
<template v-else> <template v-else>
<span>명성</span><strong>{{ numberText(summary.experience) }}</strong> <span>계급</span <span>명성</span><strong>{{ numberText(summary.experience) }}</strong> <span>계급</span
><strong>{{ summary.dedicationText || '-' }}</strong> <span>전투</span ><strong>{{ summary.dedicationText || '-' }}</strong>
<span class="battle-general-extra__empty" aria-hidden="true"></span>
<strong class="battle-general-extra__empty" aria-hidden="true"></strong>
<span>전투</span
><strong>{{ numberText(summary.warnum) }}<template v-if="summary.warnum != null"></template></strong> ><strong>{{ numberText(summary.warnum) }}<template v-if="summary.warnum != null"></template></strong>
<span>승리</span><strong>{{ numberText(summary.wins) }}</strong> <span>패배</span <span>계략</span><strong>{{ numberText(summary.strategies) }}</strong>
><strong>{{ numberText(summary.losses) }}</strong> <span>계략</span
><strong>{{ numberText(summary.strategies) }}</strong>
<template v-if="summary.serviceYears !== undefined"> <template v-if="summary.serviceYears !== undefined">
<span>사관</span <span>사관</span
><strong ><strong
@@ -73,11 +74,28 @@ const killRate = computed(() => {
}}<template v-if="summary.serviceYears != null"></template></strong }}<template v-if="summary.serviceYears != null"></template></strong
> >
</template> </template>
<template v-else>
<span class="battle-general-extra__empty" aria-hidden="true"></span>
<strong class="battle-general-extra__empty" aria-hidden="true"></strong>
</template>
<template v-if="showWinRate">
<span>승률</span><strong>{{ winRate }}</strong>
</template>
<template v-else>
<span class="battle-general-extra__empty" aria-hidden="true"></span>
<strong class="battle-general-extra__empty" aria-hidden="true"></strong>
</template>
<span>승리</span><strong>{{ numberText(summary.wins) }}</strong> <span>패배</span
><strong>{{ numberText(summary.losses) }}</strong>
<template v-if="showWinRate">
<span>살상률</span><strong>{{ killRate }}</strong>
</template>
<template v-else>
<span class="battle-general-extra__empty" aria-hidden="true"></span>
<strong class="battle-general-extra__empty" aria-hidden="true"></strong>
</template>
<span>사살</span><strong>{{ numberText(summary.killCrew) }}</strong> <span>피살</span <span>사살</span><strong>{{ numberText(summary.killCrew) }}</strong> <span>피살</span
><strong>{{ numberText(summary.deathCrew) }}</strong> ><strong>{{ numberText(summary.deathCrew) }}</strong>
<template v-if="showWinRate">
<span>승률</span><strong>{{ winRate }}</strong> <span>살상률</span><strong>{{ killRate }}</strong>
</template>
<span class="battle-general-extra__recent-label">최근 전투</span> <span class="battle-general-extra__recent-label">최근 전투</span>
<strong class="battle-general-extra__recent-value"> <strong class="battle-general-extra__recent-value">
{{ formatServerDateTime(summary.recentWar, { format: 'monthDayTime', fallback: '-' }) }} {{ formatServerDateTime(summary.recentWar, { format: 'monthDayTime', fallback: '-' }) }}
@@ -113,6 +131,10 @@ const killRate = computed(() => {
white-space: nowrap; white-space: nowrap;
} }
.battle-general-extra > .battle-general-extra__empty {
color: transparent;
}
.battle-general-extra > .battle-general-extra__recent-label { .battle-general-extra > .battle-general-extra__recent-label {
grid-column: 1; grid-column: 1;
} }