feat: show sortie recommendation reasons
This commit is contained in:
@@ -404,6 +404,9 @@ try {
|
||||
if (!damageStrategy) {
|
||||
throw new Error(`Expected ${partner.id} to have a damaging strategy for the pursuit-ready UI fixture.`);
|
||||
}
|
||||
partner.x = target.x;
|
||||
partner.y = target.y - 1;
|
||||
scene.positionUnitView(partner);
|
||||
stageTargeting({
|
||||
user: partner,
|
||||
action: damageStrategy.command,
|
||||
@@ -3911,6 +3914,140 @@ try {
|
||||
})}`
|
||||
);
|
||||
|
||||
const midRecommendationToggleBounds = midFormationPortraitState?.sortieRecommendationBrowser?.toggleButtonBounds;
|
||||
const midRecommendationSelectionBefore = {
|
||||
selectedUnitIds: [...(midFormationPortraitState?.selectedSortieUnitIds ?? [])],
|
||||
formationAssignments: { ...(midFormationPortraitState?.sortieFormationAssignments ?? {}) },
|
||||
itemAssignments: { ...(midFormationPortraitState?.sortieItemAssignments ?? {}) }
|
||||
};
|
||||
assert(
|
||||
isFiniteBounds(midRecommendationToggleBounds),
|
||||
`Expected the mid-campaign formation to expose the recommendation browser toggle: ${JSON.stringify(midFormationPortraitState?.sortieRecommendationBrowser)}`
|
||||
);
|
||||
await page.mouse.click(
|
||||
midRecommendationToggleBounds.x + midRecommendationToggleBounds.width / 2,
|
||||
midRecommendationToggleBounds.y + midRecommendationToggleBounds.height / 2
|
||||
);
|
||||
await page.waitForFunction(
|
||||
() => window.__HEROS_DEBUG__?.camp()?.sortieRecommendationBrowser?.open === true,
|
||||
undefined,
|
||||
{ timeout: 30000 }
|
||||
);
|
||||
const midRecommendationOpenState = await page.evaluate(() => window.__HEROS_DEBUG__?.camp());
|
||||
const midRecommendationTarget = midRecommendationOpenState?.sortieRecommendationBrowser?.cards?.find(
|
||||
(card) => card.applicable && !card.current &&
|
||||
card.selectedUnitIds.some((unitId) => !midRecommendationSelectionBefore.selectedUnitIds.includes(unitId)) &&
|
||||
midRecommendationSelectionBefore.selectedUnitIds.some((unitId) => !card.selectedUnitIds.includes(unitId)) &&
|
||||
isFiniteBounds(card.backgroundBounds) && isFiniteBounds(card.compareButtonBounds)
|
||||
);
|
||||
assert(
|
||||
midRecommendationTarget && isFiniteBounds(midRecommendationOpenState?.sortieRecommendationBrowser?.closeButtonBounds),
|
||||
`Expected an applicable recommendation card that differs from the current formation: ${JSON.stringify(midRecommendationOpenState?.sortieRecommendationBrowser)}`
|
||||
);
|
||||
await page.mouse.move(
|
||||
midRecommendationTarget.backgroundBounds.x + midRecommendationTarget.backgroundBounds.width / 2,
|
||||
midRecommendationTarget.backgroundBounds.y + midRecommendationTarget.backgroundBounds.height / 2
|
||||
);
|
||||
await page.waitForFunction(
|
||||
(planId) => window.__HEROS_DEBUG__?.camp()?.sortieRecommendationBrowser?.reasonPanel?.planId === planId,
|
||||
midRecommendationTarget.id,
|
||||
{ timeout: 30000 }
|
||||
);
|
||||
const midRecommendationHoverState = await page.evaluate(() => window.__HEROS_DEBUG__?.camp());
|
||||
const midRecommendationHoverBrowser = midRecommendationHoverState?.sortieRecommendationBrowser;
|
||||
const midRecommendationReasonPanel = midRecommendationHoverBrowser?.reasonPanel;
|
||||
const midRecommendationReasonRows = midRecommendationReasonPanel?.rows ?? [];
|
||||
const midRecommendationRequiredRow = midRecommendationReasonRows.find((row) => row.unitId === 'zhuge-liang');
|
||||
const midRecommendationIncomingIds = midRecommendationTarget.selectedUnitIds.filter(
|
||||
(unitId) => !midRecommendationSelectionBefore.selectedUnitIds.includes(unitId)
|
||||
);
|
||||
const midRecommendationOutgoingIds = midRecommendationSelectionBefore.selectedUnitIds.filter(
|
||||
(unitId) => !midRecommendationTarget.selectedUnitIds.includes(unitId)
|
||||
);
|
||||
const midRecommendationOfficerNames = Object.fromEntries(
|
||||
(midRecommendationHoverState?.sortiePortraitRoster ?? []).map((unit) => [unit.id, unit.name])
|
||||
);
|
||||
const midRecommendationFirstOutgoingName = midRecommendationOfficerNames[midRecommendationOutgoingIds[0]];
|
||||
assert(
|
||||
midRecommendationHoverBrowser?.hoveredPlanId === midRecommendationTarget.id &&
|
||||
midRecommendationReasonPanel?.emptyVisible === false &&
|
||||
sameJsonValue(midRecommendationReasonRows.map((row) => row.unitId), midRecommendationTarget.selectedUnitIds) &&
|
||||
midRecommendationReasonRows.every(
|
||||
(row) => row.fullReason === midRecommendationTarget.unitReasons[row.unitId] &&
|
||||
isFiniteBounds(row.bounds) && boundsInside(row.bounds, midRecommendationReasonPanel.bounds) &&
|
||||
isFiniteBounds(row.memberBounds) && boundsInside(row.memberBounds, row.bounds) &&
|
||||
isFiniteBounds(row.reasonBounds) && boundsInside(row.reasonBounds, row.bounds)
|
||||
) &&
|
||||
midRecommendationIncomingIds.every(
|
||||
(unitId) => midRecommendationReasonRows.find((row) => row.unitId === unitId)?.state === 'incoming'
|
||||
) &&
|
||||
midRecommendationIncomingIds.length > 0 &&
|
||||
midRecommendationOutgoingIds.length > 0 &&
|
||||
midRecommendationFirstOutgoingName &&
|
||||
midRecommendationReasonPanel.changeSummary.includes(`OUT ${midRecommendationFirstOutgoingName}`) &&
|
||||
(midRecommendationRequiredRow?.state === 'required' || midRecommendationRequiredRow?.state === 'required-role') &&
|
||||
midRecommendationRequiredRow.fullReason === '이번 전투의 필수 출전 무장입니다. · 고유 동남풍 화계' &&
|
||||
midRecommendationRequiredRow.reason.startsWith('고유 동남풍 화계') &&
|
||||
sameJsonValue(
|
||||
{
|
||||
selectedUnitIds: midRecommendationHoverState?.selectedSortieUnitIds,
|
||||
formationAssignments: midRecommendationHoverState?.sortieFormationAssignments,
|
||||
itemAssignments: midRecommendationHoverState?.sortieItemAssignments
|
||||
},
|
||||
midRecommendationSelectionBefore
|
||||
),
|
||||
`Expected recommendation hover to render every source-backed officer reason inside the FHD panel without mutating formation: ${JSON.stringify({
|
||||
target: midRecommendationTarget,
|
||||
browser: midRecommendationHoverBrowser,
|
||||
before: midRecommendationSelectionBefore,
|
||||
after: {
|
||||
selectedUnitIds: midRecommendationHoverState?.selectedSortieUnitIds,
|
||||
formationAssignments: midRecommendationHoverState?.sortieFormationAssignments,
|
||||
itemAssignments: midRecommendationHoverState?.sortieItemAssignments
|
||||
}
|
||||
})}`
|
||||
);
|
||||
|
||||
await page.mouse.click(
|
||||
midRecommendationTarget.compareButtonBounds.x + midRecommendationTarget.compareButtonBounds.width / 2,
|
||||
midRecommendationTarget.compareButtonBounds.y + midRecommendationTarget.compareButtonBounds.height / 2
|
||||
);
|
||||
await page.mouse.move(40, 40);
|
||||
await page.waitForFunction(
|
||||
(planId) => {
|
||||
const state = window.__HEROS_DEBUG__?.camp();
|
||||
const browser = state?.sortieRecommendationBrowser;
|
||||
return browser?.pinnedPlanId === planId && browser?.hoveredPlanId === null && browser?.reasonPanel?.planId === planId &&
|
||||
state?.sortieComparisonPreview?.source === 'pinned-recommendation' &&
|
||||
state?.sortieComparisonAction?.kind === 'confirm-recommendation';
|
||||
},
|
||||
midRecommendationTarget.id,
|
||||
{ timeout: 30000 }
|
||||
);
|
||||
const midRecommendationPinnedState = await page.evaluate(() => window.__HEROS_DEBUG__?.camp());
|
||||
assert(
|
||||
midRecommendationPinnedState?.sortieRecommendationBrowser?.reasonPanel?.rows?.length === midRecommendationTarget.selectedUnitIds.length &&
|
||||
sameJsonValue(
|
||||
{
|
||||
selectedUnitIds: midRecommendationPinnedState?.selectedSortieUnitIds,
|
||||
formationAssignments: midRecommendationPinnedState?.sortieFormationAssignments,
|
||||
itemAssignments: midRecommendationPinnedState?.sortieItemAssignments
|
||||
},
|
||||
midRecommendationSelectionBefore
|
||||
),
|
||||
`Expected a pinned recommendation to preserve its officer reasons without applying the formation: ${JSON.stringify(midRecommendationPinnedState?.sortieRecommendationBrowser)}`
|
||||
);
|
||||
const midRecommendationCloseBounds = midRecommendationPinnedState.sortieRecommendationBrowser.closeButtonBounds;
|
||||
await page.mouse.click(
|
||||
midRecommendationCloseBounds.x + midRecommendationCloseBounds.width / 2,
|
||||
midRecommendationCloseBounds.y + midRecommendationCloseBounds.height / 2
|
||||
);
|
||||
await page.waitForFunction(
|
||||
() => window.__HEROS_DEBUG__?.camp()?.sortieRecommendationBrowser?.open === false,
|
||||
undefined,
|
||||
{ timeout: 30000 }
|
||||
);
|
||||
|
||||
const midCoreSelectorToggle = midFormationPortraitState?.sortiePursuitPreview;
|
||||
assert(
|
||||
midCoreSelectorToggle?.selectorOpen === false &&
|
||||
|
||||
Reference in New Issue
Block a user