fix(scan): repair pre-existing tsc errors so the build is green

The scan feature had 16 tsc errors from refactor drift; npm run build failed.

- modals/hooks/* are five levels deep but imported ../../../../lib (four);
  corrected to ../../../../../lib.
- useScanDiagnosticsModalModel / useScanReviewQueueModalModel picked
  saveReviewSample / canSaveReviewSample / loadReviewQueue from the modal Props,
  but the components wire those through from controller.*; source them from the
  controller type instead (fixes the downstream unknown-type errors).
- useScanResultCardModel let its field-row tuple array widen to
  (string | ParsedField)[][]; annotate it Array<[string, ParsedField]> like the
  sibling hook.
- ScanTopControlsModel was missing autoScanRunning (destructured by the
  component); add it. useScanTopControlsModel does not use refreshCaptureSources,
  so its input is Omit<...,"refreshCaptureSources">.

tsc, vite build, and the electron build all pass; 74 tests green.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
AzuTear
2026-07-05 21:25:34 +02:00
parent b7dbc618b3
commit 92345ef51a
6 changed files with 27 additions and 18 deletions
@@ -60,11 +60,7 @@ export function useScanResultCardModel({
parsed,
}: Pick<ArtifactResultCardProps, "parsed">): ScanResultCardModel {
const substats = parsed.substats;
return {
levelField: getLevelField(parsed),
quality: resolveQuality(parsed.confidence),
fieldRows: [
const rows: Array<[string, ParsedField]> = [
["Name", parsed.fields.name],
["Slot", parsed.fields.slot],
["Level", getLevelField(parsed)],
@@ -72,7 +68,12 @@ export function useScanResultCardModel({
["Set", parsed.fields.setName],
["Equipped", parsed.fields.equipped],
["Substats", parsed.fields.substats],
].map(([label, field]) => ({
];
return {
levelField: getLevelField(parsed),
quality: resolveQuality(parsed.confidence),
fieldRows: rows.map(([label, field]) => ({
label,
field,
confidenceClassName: resolveFieldConfidenceClass(field),
@@ -8,6 +8,7 @@ export interface ScanTopControlsModel {
canStartAutoScan: boolean;
canStartManualScan: boolean;
canCaptureSingle: boolean;
autoScanRunning: boolean;
handleSourceChange: (event: ChangeEvent<HTMLSelectElement>) => void;
selectGenshinSource: () => void;
openSettings: () => void;
@@ -41,7 +42,7 @@ export function useScanTopControlsModel({
bridgeReady,
isScanning,
controller,
}: ScanTopControlsSectionProps): ScanTopControlsModel {
}: Omit<ScanTopControlsSectionProps, "refreshCaptureSources">): ScanTopControlsModel {
const {
setSettingsOpen,
setDiagnosticsOpen,
@@ -116,6 +117,7 @@ export function useScanTopControlsModel({
canStartAutoScan: hasSourceSelected && !isScanning && !autoScanRunning && canAutoScan && !requiresAdminForAutoScan,
canStartManualScan: hasSourceSelected && !isScanning && !autoScanRunning && canCaptureSource,
canCaptureSingle: hasSourceSelected && !isScanning && !autoScanRunning && canCaptureSource,
autoScanRunning,
handleSourceChange,
selectGenshinSource,
openSettings,
@@ -1,6 +1,6 @@
import { useCallback, type MouseEvent } from "react";
import type { ScanDetailsModalProps } from "../types";
import type { ParsedArtifactCandidate } from "../../../../lib/artifactOcrParser";
import type { ParsedArtifactCandidate } from "../../../../../lib/artifactOcrParser";
export interface ScanDetailsModalModel {
closeDetails: () => void;
@@ -1,5 +1,5 @@
import { detailFingerprint } from "../../../../lib/autoScanLoop";
import { sourceVersion } from "../../../../lib/genshinData";
import { detailFingerprint } from "../../../../../lib/autoScanLoop";
import { sourceVersion } from "../../../../../lib/genshinData";
import { useCallback, useMemo, type MouseEvent } from "react";
import type { ScanDiagnosticsModalProps } from "../types";
@@ -39,16 +39,20 @@ export interface ScanDiagnosticsModalModel {
canSaveReviewSample: boolean;
}
type ScanDiagnosticsController = ScanDiagnosticsModalProps["controller"];
interface UseScanDiagnosticsModalModelInput extends Pick<
ScanDiagnosticsModalProps,
| "setDetailsOpen"
| "setDiagnosticsOpen"
| "saveReviewSample"
| "canSaveReviewSample"
| "latestCapture"
| "controller"
> {
captureStatus: string;
// saveReviewSample / canSaveReviewSample live on the controller, not the modal
// props; the component wires them through from controller.* .
saveReviewSample: ScanDiagnosticsController["saveReviewSample"];
canSaveReviewSample: ScanDiagnosticsController["canSaveReviewSample"];
}
export function useScanDiagnosticsModalModel({
@@ -1,5 +1,5 @@
import { useCallback, useMemo, type MouseEvent } from "react";
import type { ReviewSampleAnalysis } from "../../../../lib/reviewSampleAnalysis";
import type { ReviewSampleAnalysis } from "../../../../../lib/reviewSampleAnalysis";
import type { ScanReviewQueueModalProps } from "../types";
export interface ScanReviewQueueRow {
@@ -18,8 +18,10 @@ export interface ScanReviewQueueModalModel {
interface UseScanReviewQueueModalModelInput extends Pick<
ScanReviewQueueModalProps,
"setReviewQueueOpen" | "loadReviewQueue"
"setReviewQueueOpen"
> {
// loadReviewQueue is wired through from controller.* by the component.
loadReviewQueue: ScanReviewQueueModalProps["controller"]["loadReviewQueue"];
reviewAnalysis: ReviewSampleAnalysis;
reviewSampleTotal: number;
}
@@ -1,6 +1,6 @@
import { useCallback, type ChangeEvent, type MouseEvent } from "react";
import type { CaptureResult, RuntimeInfo } from "../../../../../types/global";
import { clampScanLimit, clampSkipRows } from "../../../../lib/scannerSession";
import { clampScanLimit, clampSkipRows } from "../../../../../lib/scannerSession";
export interface ScanSettingsModalModel {
closeSettings: () => void;