fix: fallback to default semantic colors when config is incomplete

Prevent runtime crashes when custom semanticColors omit baseboard, cabinet, or wall entries.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
a1518 2026-06-30 23:03:29 -07:00
parent 70499176d6
commit bf6b6cf502
4 changed files with 34 additions and 12 deletions

View File

@ -1 +1 @@
{"version":3,"file":"maskSemanticPalette.d.ts","sourceRoot":"","sources":["../../src/utils/maskSemanticPalette.ts"],"names":[],"mappings":"AAKA,MAAM,MAAM,iBAAiB,GAAG;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,GAAG,EAAE,MAAM,CAAC;IACZ,+BAA+B;IAC/B,GAAG,EAAE;QAAE,CAAC,EAAE,MAAM,CAAC;QAAC,CAAC,EAAE,MAAM,CAAC;QAAC,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC;CAC1C,CAAC;AAEF,0BAA0B;AAC1B,eAAO,MAAM,oBAAoB,EAAE,iBAAiB,EAUnD,CAAC;AAEF,eAAO,MAAM,uBAAuB,cAAc,CAAC;AAiEnD,wCAAwC;AACxC,wBAAgB,0BAA0B,CACxC,CAAC,EAAE,MAAM,EACT,CAAC,EAAE,MAAM,EACT,CAAC,EAAE,MAAM,GACR,MAAM,CA8BR;AAED,wBAAgB,sBAAsB,CAAC,IAAI,EAAE,MAAM,GAAG,iBAAiB,GAAG,SAAS,CAGlF;AAED;;GAEG;AACH,wBAAgB,sBAAsB,CACpC,CAAC,EAAE,MAAM,EACT,CAAC,EAAE,MAAM,EACT,CAAC,EAAE,MAAM,GACR,OAAO,CAYT;AAED,wBAAgB,gBAAgB,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,GAAG,OAAO,CAEzE;AAED,qBAAqB;AACrB,eAAO,MAAM,0BAA0B,aAAuC,CAAC;AAE/E,eAAe;AACf,eAAO,MAAM,eAAe,aAM1B,CAAC;AAEH,iBAAiB;AACjB,eAAO,MAAM,kBAAkB,aAI7B,CAAC;AAEH,wBAAgB,0BAA0B,IAAI,GAAG,CAAC,MAAM,CAAC,CAExD;AAED,wBAAgB,gBAAgB,IAAI,GAAG,CAAC,MAAM,CAAC,CAE9C;AAED,wBAAgB,mBAAmB,IAAI,GAAG,CAAC,MAAM,CAAC,CAEjD"}
{"version":3,"file":"maskSemanticPalette.d.ts","sourceRoot":"","sources":["../../src/utils/maskSemanticPalette.ts"],"names":[],"mappings":"AAKA,MAAM,MAAM,iBAAiB,GAAG;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,GAAG,EAAE,MAAM,CAAC;IACZ,+BAA+B;IAC/B,GAAG,EAAE;QAAE,CAAC,EAAE,MAAM,CAAC;QAAC,CAAC,EAAE,MAAM,CAAC;QAAC,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC;CAC1C,CAAC;AAEF,0BAA0B;AAC1B,eAAO,MAAM,oBAAoB,EAAE,iBAAiB,EAUnD,CAAC;AAEF,eAAO,MAAM,uBAAuB,cAAc,CAAC;AA8EnD,wCAAwC;AACxC,wBAAgB,0BAA0B,CACxC,CAAC,EAAE,MAAM,EACT,CAAC,EAAE,MAAM,EACT,CAAC,EAAE,MAAM,GACR,MAAM,CA8BR;AAED,wBAAgB,sBAAsB,CAAC,IAAI,EAAE,MAAM,GAAG,iBAAiB,GAAG,SAAS,CAGlF;AAED;;GAEG;AACH,wBAAgB,sBAAsB,CACpC,CAAC,EAAE,MAAM,EACT,CAAC,EAAE,MAAM,EACT,CAAC,EAAE,MAAM,GACR,OAAO,CAYT;AAED,wBAAgB,gBAAgB,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,GAAG,OAAO,CAEzE;AAED,qBAAqB;AACrB,eAAO,MAAM,0BAA0B,aAAuC,CAAC;AAE/E,eAAe;AACf,eAAO,MAAM,eAAe,aAM1B,CAAC;AAEH,iBAAiB;AACjB,eAAO,MAAM,kBAAkB,aAI7B,CAAC;AAEH,wBAAgB,0BAA0B,IAAI,GAAG,CAAC,MAAM,CAAC,CAExD;AAED,wBAAgB,gBAAgB,IAAI,GAAG,CAAC,MAAM,CAAC,CAE9C;AAED,wBAAgB,mBAAmB,IAAI,GAAG,CAAC,MAAM,CAAC,CAEjD"}

View File

@ -24,6 +24,13 @@ function buildSemanticRgb(colors) {
},
}));
}
function getDefaultSemanticEntry(name) {
const color = MASK_SEMANTIC_COLORS.find(c => c.name === name);
return {
name: color.name,
rgb: { r: color.bgr.r, g: color.bgr.g, b: color.bgr.b },
};
}
function getSemanticContext() {
const revision = getMaskRuntimeRevision();
if (contextRevision === revision && cachedContext) {
@ -31,9 +38,11 @@ function getSemanticContext() {
}
const mask = getMaskSegmentRuntimeConfig().mask;
const semanticRgb = buildSemanticRgb(mask.semanticColors);
const baseboardRgb = semanticRgb.find(entry => entry.name === BASEBOARD_SEMANTIC_NAME);
const cabinetRgb = semanticRgb.find(entry => entry.name === 'cabinet');
const wallRgb = semanticRgb.find(entry => entry.name === 'wall');
const baseboardRgb = semanticRgb.find(entry => entry.name === BASEBOARD_SEMANTIC_NAME) ?? getDefaultSemanticEntry(BASEBOARD_SEMANTIC_NAME);
const cabinetRgb = semanticRgb.find(entry => entry.name === 'cabinet') ??
getDefaultSemanticEntry('cabinet');
const wallRgb = semanticRgb.find(entry => entry.name === 'wall') ??
getDefaultSemanticEntry('wall');
const maxDist = mask.baseboardMaxColorDist;
cachedContext = {
baseboardMaxColorDistSq: maxDist * maxDist,
@ -75,7 +84,7 @@ export function classifyBgrPixelToSemantic(b, g, r) {
best = entry;
}
}
return best.name;
return best?.name ?? 'wall';
}
export function getSemanticColorByName(name) {
const colors = getMaskSegmentRuntimeConfig().mask.semanticColors;

File diff suppressed because one or more lines are too long

View File

@ -52,6 +52,14 @@ function buildSemanticRgb(colors: MaskSemanticColor[]): SemanticRgbEntry[] {
}));
}
function getDefaultSemanticEntry(name: string): SemanticRgbEntry {
const color = MASK_SEMANTIC_COLORS.find(c => c.name === name)!;
return {
name: color.name,
rgb: { r: color.bgr.r, g: color.bgr.g, b: color.bgr.b },
};
}
function getSemanticContext(): SemanticContext {
const revision = getMaskRuntimeRevision();
if (contextRevision === revision && cachedContext) {
@ -60,11 +68,16 @@ function getSemanticContext(): SemanticContext {
const mask = getMaskSegmentRuntimeConfig().mask;
const semanticRgb = buildSemanticRgb(mask.semanticColors);
const baseboardRgb = semanticRgb.find(
entry => entry.name === BASEBOARD_SEMANTIC_NAME,
)!;
const cabinetRgb = semanticRgb.find(entry => entry.name === 'cabinet')!;
const wallRgb = semanticRgb.find(entry => entry.name === 'wall')!;
const baseboardRgb =
semanticRgb.find(
entry => entry.name === BASEBOARD_SEMANTIC_NAME,
) ?? getDefaultSemanticEntry(BASEBOARD_SEMANTIC_NAME);
const cabinetRgb =
semanticRgb.find(entry => entry.name === 'cabinet') ??
getDefaultSemanticEntry('cabinet');
const wallRgb =
semanticRgb.find(entry => entry.name === 'wall') ??
getDefaultSemanticEntry('wall');
const maxDist = mask.baseboardMaxColorDist;
cachedContext = {
@ -122,7 +135,7 @@ export function classifyBgrPixelToSemantic(
}
}
return best.name;
return best?.name ?? 'wall';
}
export function getSemanticColorByName(name: string): MaskSemanticColor | undefined {