@things-factory/figure-ui 10.1.26 โ 10.1.28
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/client/graphql/index.ts +23 -0
- package/client/modeller/base-box.ts +104 -0
- package/client/modeller/figure-animations.ts +253 -32
- package/client/modeller/figure-canvas.ts +18 -3
- package/client/modeller/figure-inspector.ts +292 -3
- package/client/modeller/figure-preview.ts +57 -2
- package/client/modeller/figure-report.ts +9 -4
- package/client/modeller/figure-side.ts +9 -1
- package/client/modeller/figure-source.ts +24 -4
- package/client/modeller/figure-view.ts +20 -0
- package/client/modeller/joint-edits.ts +262 -0
- package/client/modeller/joint-gizmo.ts +118 -0
- package/client/modeller/pose-defaults.ts +67 -0
- package/client/modeller/proposal.ts +9 -3
- package/client/modeller/scene-budget.ts +31 -40
- package/client/pages/figure-list-page.ts +4 -9
- package/client/pages/figure-modeller-page.ts +124 -41
- package/dist-client/graphql/index.d.ts +7 -0
- package/dist-client/graphql/index.js +21 -0
- package/dist-client/graphql/index.js.map +1 -1
- package/dist-client/modeller/base-box.d.ts +47 -0
- package/dist-client/modeller/base-box.js +52 -0
- package/dist-client/modeller/base-box.js.map +1 -0
- package/dist-client/modeller/figure-animations.d.ts +29 -0
- package/dist-client/modeller/figure-animations.js +228 -25
- package/dist-client/modeller/figure-animations.js.map +1 -1
- package/dist-client/modeller/figure-canvas.d.ts +9 -0
- package/dist-client/modeller/figure-canvas.js +14 -3
- package/dist-client/modeller/figure-canvas.js.map +1 -1
- package/dist-client/modeller/figure-inspector.d.ts +37 -0
- package/dist-client/modeller/figure-inspector.js +253 -2
- package/dist-client/modeller/figure-inspector.js.map +1 -1
- package/dist-client/modeller/figure-preview.d.ts +15 -0
- package/dist-client/modeller/figure-preview.js +48 -2
- package/dist-client/modeller/figure-preview.js.map +1 -1
- package/dist-client/modeller/figure-report.d.ts +3 -2
- package/dist-client/modeller/figure-report.js +9 -4
- package/dist-client/modeller/figure-report.js.map +1 -1
- package/dist-client/modeller/figure-side.d.ts +5 -1
- package/dist-client/modeller/figure-side.js +12 -0
- package/dist-client/modeller/figure-side.js.map +1 -1
- package/dist-client/modeller/figure-source.d.ts +15 -0
- package/dist-client/modeller/figure-source.js +8 -4
- package/dist-client/modeller/figure-source.js.map +1 -1
- package/dist-client/modeller/figure-view.d.ts +16 -0
- package/dist-client/modeller/figure-view.js +15 -0
- package/dist-client/modeller/figure-view.js.map +1 -1
- package/dist-client/modeller/joint-edits.d.ts +49 -0
- package/dist-client/modeller/joint-edits.js +223 -0
- package/dist-client/modeller/joint-edits.js.map +1 -0
- package/dist-client/modeller/joint-gizmo.d.ts +31 -0
- package/dist-client/modeller/joint-gizmo.js +104 -0
- package/dist-client/modeller/joint-gizmo.js.map +1 -0
- package/dist-client/modeller/pose-defaults.d.ts +9 -0
- package/dist-client/modeller/pose-defaults.js +35 -0
- package/dist-client/modeller/pose-defaults.js.map +1 -0
- package/dist-client/modeller/proposal.d.ts +1 -1
- package/dist-client/modeller/proposal.js +8 -3
- package/dist-client/modeller/proposal.js.map +1 -1
- package/dist-client/modeller/scene-budget.d.ts +31 -34
- package/dist-client/modeller/scene-budget.js +28 -37
- package/dist-client/modeller/scene-budget.js.map +1 -1
- package/dist-client/pages/figure-list-page.js +4 -9
- package/dist-client/pages/figure-list-page.js.map +1 -1
- package/dist-client/pages/figure-modeller-page.d.ts +43 -0
- package/dist-client/pages/figure-modeller-page.js +121 -40
- package/dist-client/pages/figure-modeller-page.js.map +1 -1
- package/dist-client/tsconfig.tsbuildinfo +1 -1
- package/dist-server/tsconfig.tsbuildinfo +1 -1
- package/package.json +3 -3
- package/test/ai-proposal-contract.test.ts +16 -11
- package/test/base-box.test.ts +154 -0
- package/test/figure-source.test.ts +32 -0
- package/test/joint-edits.test.ts +165 -0
- package/test/joint-gizmo.test.ts +174 -0
- package/test/pose-defaults.test.ts +71 -0
- package/test/preview-board-depth.test.ts +27 -0
- package/test/scene-budget.test.ts +53 -0
- package/translations/en.json +37 -2
- package/translations/ja.json +37 -2
- package/translations/ko.json +37 -2
- package/translations/ms.json +37 -2
- package/translations/zh.json +37 -2
|
@@ -4,7 +4,8 @@ import { customElement, property, query, state } from 'lit/decorators.js';
|
|
|
4
4
|
import { i18next, localize } from '@operato/i18n';
|
|
5
5
|
import { compile, validate } from '@hatiolab/figure-model';
|
|
6
6
|
import { create, registerFigure } from '@hatiolab/things-scene';
|
|
7
|
-
import { DEFAULT_VIEW, sceneLook, WORKBENCH } from './figure-view.js';
|
|
7
|
+
import { DEFAULT_VIEW, previewBoardDepth, sceneLook, WORKBENCH } from './figure-view.js';
|
|
8
|
+
import { poseChanges } from './pose-defaults.js';
|
|
8
9
|
/**
|
|
9
10
|
* ์ ์ ์ค์ธ ๊ฒ์ **๋๋ฉด์ ๋์์ ๋**์ ๋ชจ์ต.
|
|
10
11
|
*
|
|
@@ -126,6 +127,24 @@ let FigurePreview = class FigurePreview extends localize(i18next)(LitElement) {
|
|
|
126
127
|
align-items: center;
|
|
127
128
|
gap: 8px;
|
|
128
129
|
}
|
|
130
|
+
/*
|
|
131
|
+
๋ง๋ ์์ ๋๋ ๋จ์ถ. ์์ธ๋ฅผ ๋ง๋ ์๋ฆฌ์ ์์ด์ผ ใ์ง๊ธ ์ด๊ฒ์ ๊ธฐ๋ณธ์ผ๋กใ๊ฐ ์ฝํ๋ค.
|
|
132
|
+
์ํ ๊ฒ์ด ์์ ๋๋ง ๋์ค๋ฏ๋ก, ๋ ์ ์๋ ์นธ์ด ์๋๋ค.
|
|
133
|
+
*/
|
|
134
|
+
div[clips] button[pose] {
|
|
135
|
+
align-self: stretch;
|
|
136
|
+
padding: 4px 8px;
|
|
137
|
+
font: inherit;
|
|
138
|
+
font-size: 0.7rem;
|
|
139
|
+
color: rgba(255, 255, 255, 0.92);
|
|
140
|
+
background-color: rgba(255, 255, 255, 0.14);
|
|
141
|
+
border: 1px solid rgba(255, 255, 255, 0.22);
|
|
142
|
+
border-radius: 5px;
|
|
143
|
+
cursor: pointer;
|
|
144
|
+
}
|
|
145
|
+
div[clips] button[pose]:hover {
|
|
146
|
+
background-color: rgba(255, 255, 255, 0.24);
|
|
147
|
+
}
|
|
129
148
|
div[clips] span[drive] {
|
|
130
149
|
opacity: 0.6;
|
|
131
150
|
font-size: 0.66rem;
|
|
@@ -176,8 +195,22 @@ let FigurePreview = class FigurePreview extends localize(i18next)(LitElement) {
|
|
|
176
195
|
* ๋ฃ์ ์๋ฆฌ๋ฅผ ๋ชป ์ฐพ๋๋ค.
|
|
177
196
|
*/
|
|
178
197
|
renderDrivers(clips, parameters) {
|
|
198
|
+
/*
|
|
199
|
+
์ง๊ธ ์ธ์ด ์์ธ๋ฅผ ๊ธฐ๋ณธ๊ฐ์ผ๋ก ์ํ๋ ์๋ฆฌ. **๋ง๋ ์์ ๋๋ค** โ ์์ธ๋ฅผ ๋ง๋ ๊ณณ์ด ์ฌ๊ธฐ๋ผ,
|
|
200
|
+
๊ฐ์ ์ฝ์ด ํ๋ผ๋ฏธํฐ ์นธ์ผ๋ก ์ฎ๊ฒจ ์ ๋ ์๋ณต์ด ์์ด์ง๋ค. ์ํ ๊ฒ์ด ์์ผ๋ฉด ์์ ์ ๋์จ๋ค.
|
|
201
|
+
*/
|
|
202
|
+
const changes = poseChanges(this.draft, this.giving);
|
|
179
203
|
return html `
|
|
180
204
|
<div clips>
|
|
205
|
+
${changes.length > 0
|
|
206
|
+
? html `<button
|
|
207
|
+
pose
|
|
208
|
+
title=${i18next.t('figure.text.pose-as-default-explained')}
|
|
209
|
+
@click=${() => this.poseAsDefault()}
|
|
210
|
+
>
|
|
211
|
+
${i18next.t('figure.button.pose-as-default')}
|
|
212
|
+
</button>`
|
|
213
|
+
: ''}
|
|
181
214
|
${parameters.map(parameter => {
|
|
182
215
|
const range = parameter.range;
|
|
183
216
|
const value = this.giving[parameter.name] ?? parameter.default ?? range?.min ?? 0;
|
|
@@ -237,6 +270,15 @@ let FigurePreview = class FigurePreview extends localize(i18next)(LitElement) {
|
|
|
237
270
|
this.giving = { ...this.giving, [name]: value };
|
|
238
271
|
this.tellInstances('parameters', this.giving);
|
|
239
272
|
}
|
|
273
|
+
/**
|
|
274
|
+
* ์ธ์ด ์์ธ๋ฅผ ๊ธฐ๋ณธ๊ฐ์ผ๋ก โ **์
์ ์ฌ๊ธฐ์ ํ์ง ์๋๋ค.**
|
|
275
|
+
*
|
|
276
|
+
* ์ด์์ ์ฅ๊ณ ์๋ ๊ฒ์ ํ์ด์ง์ด๊ณ , ๋๋๋ฆฌ๊ธฐ์ ใ์ ์ฅ ์ ๋จใ๋ ๊ฑฐ๊ธฐ์ ๋งค๊ธด๋ค. ์ฌ๊ธฐ์
|
|
277
|
+
* ์ด์์ ๋ง๋ค์ด ๋ณด๋ด๋ฉด ๊ทธ ์
์ด ๋ ๊ณณ์ผ๋ก ๊ฐ๋ฆฐ๋ค. ๋ฏผ ๊ฐ๋ง ์ฌ๋ฆฐ๋ค.
|
|
278
|
+
*/
|
|
279
|
+
poseAsDefault() {
|
|
280
|
+
this.dispatchEvent(new CustomEvent('pose-as-default', { detail: { values: { ...this.giving } }, bubbles: true, composed: true }));
|
|
281
|
+
}
|
|
240
282
|
tellInstances(key, values) {
|
|
241
283
|
for (const component of this.scene?.root?.components ?? []) {
|
|
242
284
|
component.set?.(key, { ...values });
|
|
@@ -368,7 +410,7 @@ let FigurePreview = class FigurePreview extends localize(i18next)(LitElement) {
|
|
|
368
410
|
์ด๋ ๊ฒฝ์ฐ์๋ ๋ด๊ธฐ๋ ๊ฒฝ๊ณ๋ง ์ก๋๋ค. ๋ฐ๋ฅ ๊ธฐ๋ฐ์ ๊ฐ์ฅ ํฐ ๊ฒ์ ํค๊น์ง, ์ฒ์ ๊ธฐ๋ฐ์
|
|
369
411
|
์ฒ์ฅ๊น์ง๋ค. ๋ฐฐ์น๋ฅผ ๋์ด๋ก ์ฎ๊ธฐ๋ ๊ณ์ฐ์ ์ฌ๊ธฐ์ ๋ค์ ์ฐ๋ฉด ๊ทธ๊ฒ์ด ๋ ๋ฒ์งธ๊ฐ ๋๋ค.
|
|
370
412
|
*/
|
|
371
|
-
depth:
|
|
413
|
+
depth: previewBoardDepth(source, view.ceilingHeight, biggest)
|
|
372
414
|
};
|
|
373
415
|
this.scene = create({
|
|
374
416
|
target: this.stage,
|
|
@@ -424,6 +466,10 @@ __decorate([
|
|
|
424
466
|
property({ type: Object }),
|
|
425
467
|
__metadata("design:type", Object)
|
|
426
468
|
], FigurePreview.prototype, "source", void 0);
|
|
469
|
+
__decorate([
|
|
470
|
+
property({ type: Object }),
|
|
471
|
+
__metadata("design:type", Object)
|
|
472
|
+
], FigurePreview.prototype, "draft", void 0);
|
|
427
473
|
__decorate([
|
|
428
474
|
property({ type: Object }),
|
|
429
475
|
__metadata("design:type", Object)
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"figure-preview.js","sourceRoot":"","sources":["../../client/modeller/figure-preview.ts"],"names":[],"mappings":"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","sourcesContent":["import { css, html, LitElement, unsafeCSS } from 'lit'\nimport { customElement, property, query, state } from 'lit/decorators.js'\n\nimport { i18next, localize } from '@operato/i18n'\nimport { compile, validate } from '@hatiolab/figure-model'\nimport type { FigureSource } from '@hatiolab/figure-model'\nimport { create, registerFigure } from '@hatiolab/things-scene'\n\nimport { DEFAULT_VIEW, sceneLook, WORKBENCH } from './figure-view.js'\nimport type { ViewSettings } from './figure-view.js'\n\n/**\n * ์ ์ ์ค์ธ ๊ฒ์ **๋๋ฉด์ ๋์์ ๋**์ ๋ชจ์ต.\n *\n * ## ํธ์ง ์บ๋ฒ์ค๋ก๋ ๋ณผ ์ ์๋ค\n *\n * ํธ์ง ์บ๋ฒ์ค๋ ๋ถํ์ ์ปดํฌ๋ํธ๋ก ๋์ด๋๋๋ค. ๊ทธ๋์ ๋ ๊ธฐ์ค ํฌ๊ธฐ๋ค. ๊ทธ๋ฐ๋ฐ ์ด ํ์์\n * ๊ฐ ์ ๋ฐ์ **ํฌ๊ธฐ๊ฐ ๋ฌ๋ผ์ก์ ๋ ์ด๋ป๊ฒ ๋ฐ์ํ๋๊ฐ**์ ์๋ค. ๊ธฐ๋ฅ๋ง ๋์ด๋๋ ์๊ทธ๋ํ์,\n * ๋กค๋ฌ ๊ฐ์๊ฐ ๋๋ ์ปจ๋ฒ ์ด์ด๋ ๊ธฐ์ค ํฌ๊ธฐ์์๋ ์๋ฌด๊ฒ๋ ๋ณด์ฌ ์ฃผ์ง ๋ชปํ๋ค.\n *\n * ๊ทธ๋์ ์ฌ๊ธฐ์๋ ์ ์ํ ๊ฒ์ ์ค์ ๋ก ์ปดํ์ผํด `FigureInstance` ๋ก ์ธ์ด๋ค. ๋๋ฉด์ด ํ๋\n * ์ผ์ ๊ทธ๋๋ก ํ๋ค โ ์ฒญ์ฌ์ง์ ๋ฑ๋กํ๊ณ , ํ์
์ด๋ฆ๋ง ์ ์ ์ปดํฌ๋ํธ๋ฅผ ๋๋๋ค.\n *\n * ## ์ฌ๋ฌ ํฌ๊ธฐ๋ฅผ ํ ๋ฒ์ ๋๋๋ค\n *\n * ํ๋๋ง ๋์ผ๋ฉด \"์ด ํฌ๊ธฐ์์๋ ์ด๋ ๋ค\" ๋ฐ์ ์ ์ ์๋ค. ๊ธฐ์ค ํฌ๊ธฐ์ ๋๋ฆฐ ๊ฒ์ ๋๋ํ\n * ๋์์ผ ๋ฌด์์ด ๋ฐ๋ผ ๋๊ณ ๋ฌด์์ด ๊ทธ๋๋ก์ธ์ง ๋ณด์ธ๋ค.\n *\n * ## ํธ์งํ์ง ์๋๋ค\n *\n * ์ฌ๊ธฐ์ ์ง๊ฑฐ๋ ๋ ์ ์๋ค. ํธ์ง์ ์บ๋ฒ์ค์์ ํ๋ค. ๋ณด์ฌ ์ฃผ๊ธฐ๋ง ํ๋ ์๋ฆฌ๋ผ ์ฌ์\n * ๋ทฐ ๋ชจ๋๋ก ์ธ์ด๋ค.\n */\n\n/** ์ผ๋ง๋ ํค์ ๋ณด๋. */\nexport const PREVIEW_FACTOR = 2\n\n/**\n * ์ด๋ ์ถ์ ํค์ ๋์ ๋ณด๋ โ **์ผ๊ณฑ ์กฐํฉ ์ ๋ถ.**\n *\n * 1 ๋ฐฐ ยท 2 ๋ฐฐ ยท 3 ๋ฐฐ๋ฅผ ๋๋ํ ๋๋ ์๋ฆฌ๋ค. ๊ทธ๋ฌ๋ฉด ์ธ ์ถ์ด ๋ ๊ฐ์ด ๋์ด๋๋ฏ๋ก, ์ถ๋ง๋ค\n * ๋ฐ๋ก ๊ฑธ๋ฆฌ๋ ๊ท์น์ ๋์ผ๋ก ๋ณผ ์๊ฐ ์์๋ค. ์ค์ ๋ก ๋ชป ๋ณด๊ณ ๋์ด๊ฐ ๊ฒ๋ค์ด ์๋ค โ ์ปจ๋ฒ ์ด์ด์\n * ๋กค๋ฌ๊ฐ ํญ์ ์ ๋ฐ๋ผ๊ฐ๋ ๊ฒ, ๋ฌธ์ ํญ์ด ๋์ด๋ฅผ ์ ๋ฐ๋ผ๊ฐ๋ ๊ฒ์ด ๋ค ํ ์ถ๋ง ๋๋ ธ์ ๋\n * ๋๋ฌ๋๋ ๊ฒ์ด์๋ค.\n *\n * ์ฌ๋์ด๋ค. ์ฒซ์งธ๊ฐ ์ ์ํ ํฌ๊ธฐ์ด๊ณ ๋๋จธ์ง ์ผ๊ณฑ์ด ์กฐํฉ์ด๋ค. ํ ์ค๋ก ๋์ด๋์ผ๋ฉด ํ๋ฉด์\n * ์ ๋ด๊ฒจ์ **๋ค ์นธ์ฉ ๋ ์ค**๋ก ๋๋๋ค.\n */\nexport const PREVIEW_WAYS: readonly { name: string; axes: readonly ('x' | 'y' | 'z')[] }[] = [\n { name: 'base', axes: [] },\n { name: 'x', axes: ['x'] },\n { name: 'y', axes: ['y'] },\n { name: 'z', axes: ['z'] },\n { name: 'xยทy', axes: ['x', 'y'] },\n { name: 'xยทz', axes: ['x', 'z'] },\n { name: 'yยทz', axes: ['y', 'z'] },\n { name: 'xยทyยทz', axes: ['x', 'y', 'z'] }\n]\n\n/*\n * ๋์ด๋ ์ฌ๊ธฐ์ ์ ์ ํ๋ค.\n *\n * ํ๋์ ๋ฐฐ์น ๊ธฐ์ค์ ๋์ด๋ก ์ฎ๊ธฐ๋ ๊ณ์ฐ์ ์ด ํ์ผ์ด ๋ค๊ณ ์์๋ค. ์ด์ ์ฌ์ด ํ๋ค โ\n * `FigureRealObject.effectiveZPos` ๊ฐ ์ฒญ์ฌ์ง์ `placement` ์ ๋ ์ด์ด์ `heights` ๋ก ์ ํ๋ค\n * (ADR-0045, `operato-twin/design/04-decisions.md`). ๋๋ฉด์ด ๊ทธ๋ ๊ฒ ์ธ์ฐ๋ฏ๋ก ใ๋๋ฉด์ ๋์์\n * ๋์ ๋ชจ์ตใ์ ๋งํ๋ ์ด ํ๋ฉด๋ ๊ทธ๋ ๊ฒ ์ธ์์ผ ํ๋ค โ ์ฌ๊ธฐ์ `zPos` ๋ฅผ ์ ์ผ๋ฉด **์ ์ ๊ฐ์ด\n * ์ด๊ฒจ์**, ์ฌ์ด ๋ฌด์์ ํ ์ง๊ฐ ์ด ํ๋ฉด์์๋ง ์ ๋ณด์ธ๋ค.\n *\n * ๊ท์น์ด ๋ ๋ฒ์ด๋ฉด ๊ฐ๋ฆฐ๋ค. ์ค๋ ํ๋ฃจ๊ฐ ๊ทธ ์ด์ผ๊ธฐ์๋ค.\n */\n\ninterface SceneHandle {\n dispose?: () => void\n resize?: () => void\n fit?: (type?: string) => void\n root?: {\n invalidate?: () => void\n fitCameraToModel?: (margin?: number) => void\n /** ๋ณด๊ธฐ ์ค์ ์ ๋ฃ๋ ์๋ฆฌ. ์ฌ์ด ์ค์ค๋ก ๋ฐ์ํ๋ค. */\n set?: (patch: Record<string, unknown>) => void\n /** ์ธ์ ๋ ์ธ์คํด์ค๋ค. clip ์ ๋ชฐ ๋ ์ ๋ถ์ ๊ฐ์ ๊ฐ์ ์ค๋ค. */\n components?: { set?: (property: string, value: unknown) => void }[]\n }\n}\n\n@customElement('figure-preview')\nexport class FigurePreview extends localize(i18next)(LitElement) {\n static styles = css`\n :host {\n position: relative;\n display: flex;\n overflow: hidden;\n background-color: ${unsafeCSS(WORKBENCH)};\n font: var(--label-font, inherit);\n font-size: 0.76rem;\n }\n\n div[stage] {\n position: absolute;\n inset: 0;\n width: 100%;\n height: 100%;\n }\n\n /* ์ด๋ ๊ฒ์ด ๋ช ๋ฐฐ์ธ์ง โ ๋๋ํ ๋์๋ ํ๊ฐ ์์ผ๋ฉด ์ฝ์ ์ ์๋ค */\n div[legend] {\n position: absolute;\n top: 8px;\n left: 8px;\n display: flex;\n gap: 6px;\n padding: 4px 8px;\n color: rgba(255, 255, 255, 0.9);\n background-color: rgba(28, 28, 30, 0.6);\n border-radius: 6px;\n font-size: 0.72rem;\n }\n\n /*\n ์์ง์ ์กฐ์. **์ ์์๊ฐ ์ ์ ๋๋ฉ์ด์
๊ณผ ํ๋ผ๋ฏธํฐ๋ฅผ ๋ง์ ธ ๋ณผ ์ ์ผํ ์๋ฆฌ๋ค.**\n\n ๋๋ฉด์์๋ ํธ์์ด ์ด ๊ฐ์ ์ค๋ค โ ใ๋์ด 40% ๋ซํ๋คใ๋ ์ฌ์ค์ด ์ด๋์ ๊ฐ ์จ๋ค. ์ ์\n ์ค์๋ ๊ทธ ์ฌ์ค์ ์ฃผ๋ ๊ฒ์ด ์์ด์, ์๋์ง ์์ผ๋ฉด ํ๋ผ๋ฏธํฐ๋ ๊ธฐ๋ณธ๊ฐ์ ๋จธ๋ฌธ ์ฑ ์์\n ์ ์์ง์ธ๋ค. ํฌํฌ๊ฐ ์ ์ฌ๋ผ๊ฐ๋ ๊ฒ์ ์ ์์๊ฐ ใ์ ๋๋๊ตฌ๋ใ๋ก ์ฝ๊ฒ ๋๋ค.\n\n **๋ฏธ๋ฆฌ๋ณด๊ธฐ ๊ฒ์ด์ง ์์ฐ์ ๊ฒ์ด ์๋๋ค.** ์ฌ๊ธฐ์ ๋ฏผ ๊ฐ์ ์ ์ฅ๋์ง ์๋๋ค.\n */\n div[clips] {\n position: absolute;\n right: 8px;\n bottom: 8px;\n display: flex;\n flex-direction: column;\n gap: 6px;\n padding: 8px 10px;\n color: rgba(255, 255, 255, 0.92);\n background-color: rgba(28, 28, 30, 0.72);\n border-radius: 8px;\n font-size: 0.72rem;\n }\n div[clips] label {\n display: grid;\n grid-template-columns: auto 96px 34px;\n align-items: center;\n gap: 8px;\n }\n div[clips] span[drive] {\n opacity: 0.6;\n font-size: 0.66rem;\n }\n div[clips] input {\n width: 96px;\n accent-color: var(--md-sys-color-primary);\n }\n div[clips] output {\n font-variant-numeric: tabular-nums;\n text-align: right;\n opacity: 0.85;\n }\n\n /* ์ธ์ธ ์ ์๋ ์ํ๋ฅผ ๋น ํ๋ฉด์ผ๋ก ๋์ง ์๋๋ค โ ์ ์ ๋ณด์ด๋์ง ๋งํ๋ค */\n div[cannot] {\n position: absolute;\n inset: 0;\n display: flex;\n align-items: center;\n justify-content: center;\n padding: var(--spacing-large, 12px);\n text-align: center;\n line-height: 1.6;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n background-color: ${unsafeCSS(WORKBENCH)};\n }\n `\n\n /** ์ ์ ์ค์ธ ๊ฒ. ์ ์ฅ ํ์์ผ๋ก ๋ฐ๋๋ค โ ๋๋ฉด์ด ์๋นํ๋ ๊ฒ์ด ์ด ํ์์ด๋ค. */\n @property({ type: Object }) source?: FigureSource\n\n /**\n * ๋ณด๊ธฐ ์ค์ . ์ ์ฅ๋์ง ์๋๋ค(`figure-view.ts`).\n *\n * ํ๋์ ์ด ํ๋ฉด๋ง ์กฐ๋ช
๊ณผ ํ๊ฒฝ์ **ํ๋์ฝ๋ฉ**ํ๋ค. ์ ์์๊ฐ ํ๊ฒฝ ํญ์์ ๋ฌด์์ ๋ฐ๊ฟ๋\n * ํธ์ง ์บ๋ฒ์ค๋ง ๋ฌ๋ผ์ง๊ณ ์ฌ๊ธฐ๋ ๊ทธ๋๋ก์๋ค โ ๋ ํ๋ฉด์ด ๊ฐ์ ๊ฒ์ ๋ค๋ฅด๊ฒ ๋ณด์ฌ ์ฃผ์๋ค.\n */\n @property({ type: Object }) view: ViewSettings = DEFAULT_VIEW\n\n @query('div[stage]') private stage!: HTMLDivElement\n\n /** ์ธ์ธ ์ ์๋ ์ฌ์ . ์์ผ๋ฉด ์ธ์ด ๊ฒ์ด๋ค. */\n @state() private cannot = ''\n\n private scene?: SceneHandle\n /** ์ง๊ธ ์ธ์ ๋ ๊ฒ์ ๊ฐ. ๊ฐ์ผ๋ฉด ๋ค์ ์ธ์ฐ์ง ์๋๋ค. */\n private standing?: string\n private watcher?: ResizeObserver\n\n /** ์ง๊ธ ๋ฏผ clip ๋ฐฐ์. clip ์ด๋ฆ โ ์. **์ ์ฅ๋์ง ์๋๋ค.** */\n @state() private driving: Record<string, number> = {}\n /** ์ง๊ธ ๋ฏผ ํ๋ผ๋ฏธํฐ ๊ฐ. ์ด๋ฆ โ `range` ์ ๋จ์๋ก ์ฐ ์. **์ ์ฅ๋์ง ์๋๋ค.** */\n @state() private giving: Record<string, number> = {}\n\n render() {\n const clips = this.source?.animations ?? []\n const parameters = this.source?.parameters ?? []\n\n return html`\n <div stage></div>\n ${this.cannot\n ? html`<div cannot>${this.cannot}</div>`\n : html`<div legend>\n ${PREVIEW_WAYS.map(way => html`<span>${way.axes.length === 0 ? i18next.t('figure.label.preview-base') : way.name}</span>`)}\n </div>\n ${clips.length + parameters.length > 0 ? this.renderDrivers(clips, parameters) : ''}`}\n `\n }\n\n /**\n * ์์ง์ ํ๋์ ์์ก์ด ํ๋.\n *\n * ๋ ๊ฐ๋๋ฅผ **๋๊ธ์ด ๋ค๋ฅธ ์ฑ๋ก** ๋ธ๋ค. clip ์ ๋ฐฐ์์ด๋ผ 0 ์ด ๋ฉ์ถค์ด๊ณ 0~3 ์ด ๋ป์ด\n * ์์ผ๋ฉฐ, ํ๋ผ๋ฏธํฐ๋ ๋ฌผ๋ฆฌ๋์ด๋ผ ๊ทธ `range` ๊ฐ ๊ณง ๋๊ธ์ด๊ณ ๋จ์๊ฐ ๋ฐ๋ผ ๋ถ๋๋ค. ํ๋์\n * 0~1 ๋ก ๋ญ๋ฑ๊ทธ๋ฆฌ๋ฉด ใ1ใ์ด ๋ฌด์จ ๋ป์ธ์ง ๋งค๋ฒ ํท๊ฐ๋ฆฌ๊ณ , 1200mm ๋ฅผ ๋ฃ์ด ๋ณด๋ ค๋ ์ ์์๊ฐ\n * ๋ฃ์ ์๋ฆฌ๋ฅผ ๋ชป ์ฐพ๋๋ค.\n */\n private renderDrivers(\n clips: NonNullable<FigureSource['animations']>,\n parameters: NonNullable<FigureSource['parameters']>\n ) {\n return html`\n <div clips>\n ${parameters.map(parameter => {\n const range = parameter.range\n const value = this.giving[parameter.name] ?? parameter.default ?? range?.min ?? 0\n const step = range ? Math.max((range.max - range.min) / 100, 0.01) : 1\n\n return html`\n <label>\n <span>${parameter.label ?? parameter.name} <span drive>${range?.unit ?? ''}</span></span>\n <input\n type=\"range\"\n min=${range?.min ?? 0}\n max=${range?.max ?? 1}\n step=${step}\n .value=${String(value)}\n @input=${(e: Event) => this.give(parameter.name, Number((e.target as HTMLInputElement).value))}\n />\n <output>${Math.round(value)}</output>\n </label>\n `\n })}\n ${clips.map(clip => {\n const value = this.driving[clip.name] ?? 1\n\n return html`\n <label>\n <span>${clip.name} <span drive>${i18next.t('figure.label.playback-speed')}</span></span>\n <input\n type=\"range\"\n min=\"0\"\n max=\"3\"\n step=\"0.05\"\n .value=${String(value)}\n @input=${(e: Event) => this.drive(clip.name, Number((e.target as HTMLInputElement).value))}\n />\n <output>${value.toFixed(2)}</output>\n </label>\n `\n })}\n </div>\n `\n }\n\n /**\n * ์ธ์ ๋ ์ธ์คํด์ค ์ ๋ถ์ ๊ฐ์ ๊ฐ์ ์ค๋ค.\n *\n * ํ๋๋ง ๋ชฐ๋ฉด ์ธ ๋ฐฐ์จ์ด ์๋ก ๋ค๋ฅธ ์์ธ๋ก ์์, ํฌ๊ธฐ ๋ฐ์์ ๋ณด๋ ค๊ณ ๋๋ํ ๋์ ๋ป์ด\n * ์ฌ๋ผ์ง๋ค.\n */\n private drive(name: string, value: number): void {\n this.driving = { ...this.driving, [name]: value }\n this.tellInstances('clips', this.driving)\n }\n\n /**\n * ํ๋ผ๋ฏธํฐ ๊ฐ์ ์ค๋ค โ **`range` ์ ๋จ์ ๊ทธ๋๋ก๋ค.**\n *\n * 0~1 ๋ก ๋ฐ๊ฟ์ ์ฃผ์ง ์๋๋ค. ๊ทธ ํ์ฐ์ ๋ฐํ์์ ์ผ์ด๊ณ , ์ฌ๊ธฐ์ ํ ๋ฒ ๋ ํ๋ฉด ๋ ๊ณณ์ด\n * ๊ฐ๋ฆด ์ ์๋ค. ์ ์์๊ฐ ํ๋ฉด์์ ๋ณด๋ 1200 ์ด ์ฌ์ ๊ทธ๋๋ก ๊ฐ๋ค.\n */\n private give(name: string, value: number): void {\n this.giving = { ...this.giving, [name]: value }\n this.tellInstances('parameters', this.giving)\n }\n\n private tellInstances(key: 'clips' | 'parameters', values: Record<string, number>): void {\n for (const component of this.scene?.root?.components ?? []) {\n component.set?.(key, { ...values })\n }\n }\n\n /**\n * ๋ณด๊ธฐ ์ค์ ์ด ๋ฐ๋๋ฉด **๋ค์ ์ธ์ฐ์ง ์๊ณ ์ฌ์ ๋ฃ๋๋ค** โ ๋ ๊ฐ๋ง ๋นผ๊ณ .\n *\n * ์กฐ๋ช
ยทํ๊ฒฝยท๋ฐํ์ ์ฌ์ด ์ค์ค๋ก ๋ฐ์ํ๋ค(`three-capability` ์ `onchange`). ์ฌ๋ผ์ด๋๋ฅผ\n * ๋๋ ๋์ ๋ค์ ์ธ์ฐ๋ฉด ์นด๋ฉ๋ผ๊ฐ ๋งค ํ๋ ์ ์ฒ์์ผ๋ก ๋์๊ฐ๋ค.\n *\n * ์ขํ ๊ธฐ์ค๊ณผ ์ฒ์ฅ ๋์ด๋ ๋ค๋ฅด๋ค. ์ฌ์ด ๊ทธ ๋๋ก ์ธ์คํด์ค ๋์ด๋ฅผ ์ ํ๋๋ฐ, ๊ทธ ๊ณ์ฐ์ ์ธ์ธ\n * ๋ ํ ๋ฒ ๋๋ค โ ์ด๋ฏธ ์ธ์ ๋ ๊ฒ์ ๋ฃ์ด ๋ด์ผ ์๋ฆฌ๊ฐ ์ ๋ฐ๋๋ค. ๊ทธ๊ฒ๋ง ๋ค์ ์ธ์ด๋ค.\n */\n willUpdate(changed: Map<string, unknown>) {\n if (!this.hasUpdated) return\n\n if (changed.has('source')) {\n this.standUp()\n return\n }\n\n if (!changed.has('view')) return\n\n const before = changed.get('view') as ViewSettings | undefined\n const now = this.view ?? DEFAULT_VIEW\n if (before?.placement !== now.placement || before?.ceilingHeight !== now.ceilingHeight) {\n this.standUp()\n return\n }\n\n this.scene?.root?.set?.(sceneLook(now))\n }\n\n firstUpdated() {\n this.standUp()\n this.watcher = new ResizeObserver(() => this.scene?.resize?.())\n this.watcher.observe(this)\n }\n\n disconnectedCallback() {\n super.disconnectedCallback()\n this.watcher?.disconnect()\n this.watcher = undefined\n this.teardown()\n }\n\n /**\n * ์ ์ํ ๊ฒ์ ์ปดํ์ผํด ์ธ์ด๋ค.\n *\n * **ํ์์ ์ด๊ฒผ์ผ๋ฉด ์ธ์ฐ์ง ์๋๋ค.** ๋ฐ์ฏค ์ธ์ด ๊ฒ์ ๋ณด์ฌ ์ฃผ๋ฉด ๋ฌด์์ด ์๋ชป๋๋์ง ์ ์\n * ์๋ค. ํ์ ํจ๋์ด ์ด๋ฏธ ์ฌ์ ๋ฅผ ๋งํ๊ณ ์์ผ๋ฏ๋ก ์ฌ๊ธฐ์๋ ์ธ์ธ ์ ์๋ค๊ณ ๋ง ํ๋ค.\n */\n private standUp() {\n const source = this.source\n if (!source || source.parts.length === 0) {\n this.cannot = i18next.t('figure.text.preview-needs-a-part')\n this.teardown()\n return\n }\n\n const view = this.view ?? DEFAULT_VIEW\n /* ์ฌ์ด ์ด ๋๋ก ์ธ์คํด์ค ๋์ด๋ฅผ ์ ํ๋ค โ ์๋ช
์ ์ ๋ฃ์ผ๋ฉด ๋ค์ ์ธ์๋ ๊ทธ๋๋ก ์ ๋ค. */\n const signature = JSON.stringify([source, view.placement, view.ceilingHeight])\n if (this.scene && this.standing === signature) return\n\n const { errors } = validate(source)\n if (errors.length > 0) {\n this.cannot = i18next.t('figure.text.preview-blocked-by-errors')\n this.teardown()\n return\n }\n\n this.teardown()\n // ํ๋ณธ์ด ๋ฐ๋๋ฉด ๋ฏผ ๊ฐ๋ ์ฒ์์ผ๋ก ๋๋ฆฐ๋ค โ ๋ค๋ฅธ ์์ฐ์ clip ์ด๋ฆ์ด ๋จ์ผ๋ฉด ์ ๋๋ค.\n this.driving = {}\n\n try {\n registerFigure(compile(source) as never)\n\n /*\n ๋๋ฉด์ด ํ๋ ์ผ์ ๊ทธ๋๋ก ํ๋ค. ์ปดํฌ๋ํธ์๋ ํ์
์ด๋ฆ๊ณผ ์๋ฆฌยทํฌ๊ธฐ๋ง ์ ๋๋ค โ\n ์ฒญ์ฌ์ง๋ ์๋ณธ๋ ๋๋ฉด์ ๋ค์ด๊ฐ์ง ์๋๋ค.\n\n ๊ฐ์ฅ ํฐ ๊ฒ์ด ๋ค์ด๊ฐ ๋งํผ ํ์ ์ก๊ณ , ์ธ๋ก๋ก ์ค์ ๋๋ ๋๋ํ ๋๋๋ค.\n */\n const { base } = source\n const biggest = PREVIEW_FACTOR\n /** ์ด ์กฐํฉ์์ ์ถ๋ณ ๋ฐฐ์จ. ์กฐํฉ์ ๋ ์ถ๋ง ํค์ด๋ค. */\n const growth = (way: (typeof PREVIEW_WAYS)[number]) => ({\n x: way.axes.includes('x') ? PREVIEW_FACTOR : 1,\n y: way.axes.includes('y') ? PREVIEW_FACTOR : 1,\n z: way.axes.includes('z') ? PREVIEW_FACTOR : 1\n })\n // ์ฌ๋ฐฑ์ ๋๋ํ ๋๋ฉด ํ๋ฉด์์ ํ์์ด ์์์ง๋ค. ๊ฐ์ฅ ํฐ ๊ฒ์ด ๊ฒจ์ฐ ๋ค์ด๊ฐ ๋งํผ๋ง ์ก๋๋ค.\n /** ๋ค ์นธ์ฉ ๋ ์ค. */\n const COLUMNS = 4\n const cell = { x: base.x * biggest * 1.25, z: base.z * biggest * 1.25 }\n const rows = Math.ceil(PREVIEW_WAYS.length / COLUMNS)\n /*\n ์ฌ์ ๋ฑ๋ง์ด ํ์๊ณผ ๋ค๋ฅด๋ค โ `width` ๊ฐ ํ์์ x, `height` ๊ฐ z, `depth` ๊ฐ y ๋ค.\n ์ฎ๊ธฐ๋ ์ผ์ ์ฌ๊ธฐ ํ ์ค์ ๋ชจ์ ๋๋ค.\n\n `depth` ๋ฅผ ๋ ์ ๋ ์ด์ ๊ฐ ์๋ค. ์ ์ ์ผ๋ฉด ํ๋ฉด ๋ ์ถ์ ๊ธฐํํ๊ท ์ผ๋ก ์กํ์,\n ใy ๋ง ํค์ด๋คใ๊ฐ xยทz ๋ฅผ ์ ๊ฑด๋๋ฆฌ๋๋ฐ๋ ๋์ด๊ฐ ์ ์ค๋ฅธ๋ค.\n\n ๋์ด๋ **๋ฐฐ์น ๊ธฐ์ค์ด ์ ํ๋ค.** ๋ฐ๋ฅ ๊ธฐ๋ฐ์ ๋
์์ ์ฌ๋ผ์ค๊ณ , ์ฒ์ ๊ธฐ๋ฐ์ ์ฒ์ฅ์\n ๋ถ์ด ๋ด๋ ค์จ๋ค. ์ฌ๋์ ๋๋ํ ์ธ์ฐ๋ ์๋ฆฌ๋ผ ์ด๊ฒ์ด ๋์ ๋ฐ๋ก ๋ณด์ธ๋ค โ ๋ฐ๋ฅ ๊ธฐ๋ฐ์ด๋ฉด\n ๋ฐ๋ฉด์ด, ์ฒ์ ๊ธฐ๋ฐ์ด๋ฉด ์๋ฉด์ด ํ ์ค์ด ๋๋ค.\n */\n const components = PREVIEW_WAYS.map((way, at) => {\n const grow = growth(way)\n const column = at % COLUMNS\n const row = Math.floor(at / COLUMNS)\n const width = Math.round(base.x * grow.x)\n const height = Math.round(base.z * grow.z)\n const tall = Math.round(base.y * grow.y)\n\n return {\n type: source.type,\n id: `at-${way.name}`,\n // ์นธ ๊ฐ์ด๋ฐ์ ๋๋๋ค โ ํฌ๊ธฐ๊ฐ ์ ๋ง๋ค ๋ฌ๋ผ ์ผ์ชฝ์ ๋ง์ถ๋ฉด ์ค์ด ์ ์ฝํ๋ค.\n left: Math.round(column * cell.x + (cell.x - width) / 2),\n top: Math.round(row * cell.z + (cell.z - height) / 2),\n width,\n height,\n depth: tall\n }\n })\n\n const draft = {\n width: Math.round(cell.x * COLUMNS),\n height: Math.round(cell.z * rows),\n /*\n ํ์ ๋์ด๋ ๊ฐ์ฅ ํฐ ์ธ์คํด์ค๋ฅผ ๋ด์์ผ ํ๋ค. ์ ์ฃผ๋ฉด ์นด๋ฉ๋ผ๊ฐ ํ๋ฉด๋ง ๋ณด๊ณ ์๋ฆฌ๋ฅผ\n ์ก์์, ํค๊ฐ ํฐ ๋ชจ๋ธ์ ๋ฐ๋๋ง ๋ณด์ธ๋ค โ ์๊ทธ๋ํ์๋ฅผ 2 ๋ฐฐ๋ก ๋์ผ๋ฉด 2200 ์ธ๋ฐ ํ์ด\n ๊ทธ๊ฒ์ ๋ชจ๋ฅด๋ฉด ๋ฐ์นจ๋ง ํ๋ฉด์ ๋ ๋ค.\n\n ์ด๋์ ์ฌ๋ ค ๋์์ง๋ **์ฌ์ด ์ ํ๋ฏ๋ก**(`FigureRealObject.effectiveZPos`), ์ฌ๊ธฐ์๋\n ์ด๋ ๊ฒฝ์ฐ์๋ ๋ด๊ธฐ๋ ๊ฒฝ๊ณ๋ง ์ก๋๋ค. ๋ฐ๋ฅ ๊ธฐ๋ฐ์ ๊ฐ์ฅ ํฐ ๊ฒ์ ํค๊น์ง, ์ฒ์ ๊ธฐ๋ฐ์\n ์ฒ์ฅ๊น์ง๋ค. ๋ฐฐ์น๋ฅผ ๋์ด๋ก ์ฎ๊ธฐ๋ ๊ณ์ฐ์ ์ฌ๊ธฐ์ ๋ค์ ์ฐ๋ฉด ๊ทธ๊ฒ์ด ๋ ๋ฒ์งธ๊ฐ ๋๋ค.\n */\n depth: Math.round(Math.max(view.ceilingHeight, base.y * biggest) * 1.1)\n }\n\n this.scene = create({\n target: this.stage,\n model: {\n type: 'model-layer',\n width: draft.width,\n height: draft.height,\n depth: draft.depth,\n threed: true,\n sky: 'color',\n /*\n ๋ณด๊ธฐ ์ค์ ์ ๊ทธ๋๋ก ์ฃ๋๋ค.\n\n ์ฌ๊ธฐ๋ง ์กฐ๋ช
ยทํ๊ฒฝยท๋ฐํ์ ํ๋์ฝ๋ฉํ๊ณ ์์๋ค. ์ ์์๊ฐ ํ๊ฒฝ ํญ์์ ์กฐ๋ช
์\n ์ฌ๋ ค๋ ํธ์ง ์บ๋ฒ์ค๋ง ๋ฐ์์ง๊ณ ์ด ํ๋ฉด์ ๊ทธ๋๋ก์ฌ์, ๊ฐ์ ๊ฒ์ ๋ ํ๋ฉด์ด\n ๋ค๋ฅด๊ฒ ๋ณด์ฌ ์ฃผ์๋ค.\n\n `sceneLook` ์ด ์ขํ ๊ธฐ์ค๊ณผ ์ฒ์ฅ ๋์ด๋ฅผ ๋นผ๊ณ ์ค๋ค โ ์ฌ์ด ์๋ ์ด๋ฆ์ด ์๋๊ฑฐ๋\n (`ceilingHeight`) ํธ์ง ์บ๋ฒ์ค์ ์๋ฉด ์ ๋๋ ๊ฒ(`placement`)์ด๋ผ์๋ค. ๋ ๋ค ์๋์\n ์ฌ์ ๋ฑ๋ง๋ก ๋ฐ๋ก ์ฃ๋๋ค.\n */\n ...sceneLook(view),\n placement: view.placement,\n /*\n ๋ถ์ฐฉ๋ฉด์ ๋์ด. ์ฌ์ด ์ด ์๋ฆฌ๋ฅผ ๊ฐ๊ณ (`real-object.ts` ์ `sceneHeights`), ์ฒ์ ๊ธฐ๋ฐ\n ๋ํ์ด ์ฌ๊ธฐ์ ์ ๋์ด๋ฅผ ์ป๋๋ค. ๋๋ฉด์์๋ ํ์ฅ์ด ์ด ๊ฐ์ ์ค๋ค.\n */\n heights: { floor: 0, ceiling: view.ceilingHeight },\n pixelRatio: Math.min(3, (window.devicePixelRatio || 1) * 2),\n components\n },\n // ๋ณด๊ธฐ๋ง ํ๋ ์๋ฆฌ๋ค. ์ง๊ฑฐ๋ ๋ ์ ์์ด์ผ ํ๋ค.\n mode: 0\n }) as SceneHandle\n\n this.standing = signature\n this.scene.resize?.()\n this.scene.fit?.('ratio')\n this.scene.root?.fitCameraToModel?.()\n this.cannot = ''\n } catch (e) {\n // ์์ธ์ ์ง์ด๋ด์ง ์๋๋ค โ ๋์ง ๋ง์ ๊ทธ๋๋ก ๋ณด์ฌ ์ค๋ค.\n this.cannot = (e as Error).message\n }\n }\n\n private teardown() {\n this.scene?.dispose?.()\n this.scene = undefined\n this.standing = undefined\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"figure-preview.js","sourceRoot":"","sources":["../../client/modeller/figure-preview.ts"],"names":[],"mappings":"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","sourcesContent":["import { css, html, LitElement, unsafeCSS } from 'lit'\nimport { customElement, property, query, state } from 'lit/decorators.js'\n\nimport { i18next, localize } from '@operato/i18n'\nimport { compile, validate } from '@hatiolab/figure-model'\nimport type { FigureSource } from '@hatiolab/figure-model'\nimport { create, registerFigure } from '@hatiolab/things-scene'\n\nimport { DEFAULT_VIEW, previewBoardDepth, sceneLook, WORKBENCH } from './figure-view.js'\nimport type { ViewSettings } from './figure-view.js'\nimport { poseChanges } from './pose-defaults.js'\nimport type { FigureDraft } from './figure-source.js'\n\n/**\n * ์ ์ ์ค์ธ ๊ฒ์ **๋๋ฉด์ ๋์์ ๋**์ ๋ชจ์ต.\n *\n * ## ํธ์ง ์บ๋ฒ์ค๋ก๋ ๋ณผ ์ ์๋ค\n *\n * ํธ์ง ์บ๋ฒ์ค๋ ๋ถํ์ ์ปดํฌ๋ํธ๋ก ๋์ด๋๋๋ค. ๊ทธ๋์ ๋ ๊ธฐ์ค ํฌ๊ธฐ๋ค. ๊ทธ๋ฐ๋ฐ ์ด ํ์์\n * ๊ฐ ์ ๋ฐ์ **ํฌ๊ธฐ๊ฐ ๋ฌ๋ผ์ก์ ๋ ์ด๋ป๊ฒ ๋ฐ์ํ๋๊ฐ**์ ์๋ค. ๊ธฐ๋ฅ๋ง ๋์ด๋๋ ์๊ทธ๋ํ์,\n * ๋กค๋ฌ ๊ฐ์๊ฐ ๋๋ ์ปจ๋ฒ ์ด์ด๋ ๊ธฐ์ค ํฌ๊ธฐ์์๋ ์๋ฌด๊ฒ๋ ๋ณด์ฌ ์ฃผ์ง ๋ชปํ๋ค.\n *\n * ๊ทธ๋์ ์ฌ๊ธฐ์๋ ์ ์ํ ๊ฒ์ ์ค์ ๋ก ์ปดํ์ผํด `FigureInstance` ๋ก ์ธ์ด๋ค. ๋๋ฉด์ด ํ๋\n * ์ผ์ ๊ทธ๋๋ก ํ๋ค โ ์ฒญ์ฌ์ง์ ๋ฑ๋กํ๊ณ , ํ์
์ด๋ฆ๋ง ์ ์ ์ปดํฌ๋ํธ๋ฅผ ๋๋๋ค.\n *\n * ## ์ฌ๋ฌ ํฌ๊ธฐ๋ฅผ ํ ๋ฒ์ ๋๋๋ค\n *\n * ํ๋๋ง ๋์ผ๋ฉด \"์ด ํฌ๊ธฐ์์๋ ์ด๋ ๋ค\" ๋ฐ์ ์ ์ ์๋ค. ๊ธฐ์ค ํฌ๊ธฐ์ ๋๋ฆฐ ๊ฒ์ ๋๋ํ\n * ๋์์ผ ๋ฌด์์ด ๋ฐ๋ผ ๋๊ณ ๋ฌด์์ด ๊ทธ๋๋ก์ธ์ง ๋ณด์ธ๋ค.\n *\n * ## ํธ์งํ์ง ์๋๋ค\n *\n * ์ฌ๊ธฐ์ ์ง๊ฑฐ๋ ๋ ์ ์๋ค. ํธ์ง์ ์บ๋ฒ์ค์์ ํ๋ค. ๋ณด์ฌ ์ฃผ๊ธฐ๋ง ํ๋ ์๋ฆฌ๋ผ ์ฌ์\n * ๋ทฐ ๋ชจ๋๋ก ์ธ์ด๋ค.\n */\n\n/** ์ผ๋ง๋ ํค์ ๋ณด๋. */\nexport const PREVIEW_FACTOR = 2\n\n/**\n * ์ด๋ ์ถ์ ํค์ ๋์ ๋ณด๋ โ **์ผ๊ณฑ ์กฐํฉ ์ ๋ถ.**\n *\n * 1 ๋ฐฐ ยท 2 ๋ฐฐ ยท 3 ๋ฐฐ๋ฅผ ๋๋ํ ๋๋ ์๋ฆฌ๋ค. ๊ทธ๋ฌ๋ฉด ์ธ ์ถ์ด ๋ ๊ฐ์ด ๋์ด๋๋ฏ๋ก, ์ถ๋ง๋ค\n * ๋ฐ๋ก ๊ฑธ๋ฆฌ๋ ๊ท์น์ ๋์ผ๋ก ๋ณผ ์๊ฐ ์์๋ค. ์ค์ ๋ก ๋ชป ๋ณด๊ณ ๋์ด๊ฐ ๊ฒ๋ค์ด ์๋ค โ ์ปจ๋ฒ ์ด์ด์\n * ๋กค๋ฌ๊ฐ ํญ์ ์ ๋ฐ๋ผ๊ฐ๋ ๊ฒ, ๋ฌธ์ ํญ์ด ๋์ด๋ฅผ ์ ๋ฐ๋ผ๊ฐ๋ ๊ฒ์ด ๋ค ํ ์ถ๋ง ๋๋ ธ์ ๋\n * ๋๋ฌ๋๋ ๊ฒ์ด์๋ค.\n *\n * ์ฌ๋์ด๋ค. ์ฒซ์งธ๊ฐ ์ ์ํ ํฌ๊ธฐ์ด๊ณ ๋๋จธ์ง ์ผ๊ณฑ์ด ์กฐํฉ์ด๋ค. ํ ์ค๋ก ๋์ด๋์ผ๋ฉด ํ๋ฉด์\n * ์ ๋ด๊ฒจ์ **๋ค ์นธ์ฉ ๋ ์ค**๋ก ๋๋๋ค.\n */\nexport const PREVIEW_WAYS: readonly { name: string; axes: readonly ('x' | 'y' | 'z')[] }[] = [\n { name: 'base', axes: [] },\n { name: 'x', axes: ['x'] },\n { name: 'y', axes: ['y'] },\n { name: 'z', axes: ['z'] },\n { name: 'xยทy', axes: ['x', 'y'] },\n { name: 'xยทz', axes: ['x', 'z'] },\n { name: 'yยทz', axes: ['y', 'z'] },\n { name: 'xยทyยทz', axes: ['x', 'y', 'z'] }\n]\n\n/*\n * ๋์ด๋ ์ฌ๊ธฐ์ ์ ์ ํ๋ค.\n *\n * ํ๋์ ๋ฐฐ์น ๊ธฐ์ค์ ๋์ด๋ก ์ฎ๊ธฐ๋ ๊ณ์ฐ์ ์ด ํ์ผ์ด ๋ค๊ณ ์์๋ค. ์ด์ ์ฌ์ด ํ๋ค โ\n * `FigureRealObject.effectiveZPos` ๊ฐ ์ฒญ์ฌ์ง์ `placement` ์ ๋ ์ด์ด์ `heights` ๋ก ์ ํ๋ค\n * (ADR-0045, `operato-twin/design/04-decisions.md`). ๋๋ฉด์ด ๊ทธ๋ ๊ฒ ์ธ์ฐ๋ฏ๋ก ใ๋๋ฉด์ ๋์์\n * ๋์ ๋ชจ์ตใ์ ๋งํ๋ ์ด ํ๋ฉด๋ ๊ทธ๋ ๊ฒ ์ธ์์ผ ํ๋ค โ ์ฌ๊ธฐ์ `zPos` ๋ฅผ ์ ์ผ๋ฉด **์ ์ ๊ฐ์ด\n * ์ด๊ฒจ์**, ์ฌ์ด ๋ฌด์์ ํ ์ง๊ฐ ์ด ํ๋ฉด์์๋ง ์ ๋ณด์ธ๋ค.\n *\n * ๊ท์น์ด ๋ ๋ฒ์ด๋ฉด ๊ฐ๋ฆฐ๋ค. ์ค๋ ํ๋ฃจ๊ฐ ๊ทธ ์ด์ผ๊ธฐ์๋ค.\n */\n\ninterface SceneHandle {\n dispose?: () => void\n resize?: () => void\n fit?: (type?: string) => void\n root?: {\n invalidate?: () => void\n fitCameraToModel?: (margin?: number) => void\n /** ๋ณด๊ธฐ ์ค์ ์ ๋ฃ๋ ์๋ฆฌ. ์ฌ์ด ์ค์ค๋ก ๋ฐ์ํ๋ค. */\n set?: (patch: Record<string, unknown>) => void\n /** ์ธ์ ๋ ์ธ์คํด์ค๋ค. clip ์ ๋ชฐ ๋ ์ ๋ถ์ ๊ฐ์ ๊ฐ์ ์ค๋ค. */\n components?: { set?: (property: string, value: unknown) => void }[]\n }\n}\n\n@customElement('figure-preview')\nexport class FigurePreview extends localize(i18next)(LitElement) {\n static styles = css`\n :host {\n position: relative;\n display: flex;\n overflow: hidden;\n background-color: ${unsafeCSS(WORKBENCH)};\n font: var(--label-font, inherit);\n font-size: 0.76rem;\n }\n\n div[stage] {\n position: absolute;\n inset: 0;\n width: 100%;\n height: 100%;\n }\n\n /* ์ด๋ ๊ฒ์ด ๋ช ๋ฐฐ์ธ์ง โ ๋๋ํ ๋์๋ ํ๊ฐ ์์ผ๋ฉด ์ฝ์ ์ ์๋ค */\n div[legend] {\n position: absolute;\n top: 8px;\n left: 8px;\n display: flex;\n gap: 6px;\n padding: 4px 8px;\n color: rgba(255, 255, 255, 0.9);\n background-color: rgba(28, 28, 30, 0.6);\n border-radius: 6px;\n font-size: 0.72rem;\n }\n\n /*\n ์์ง์ ์กฐ์. **์ ์์๊ฐ ์ ์ ๋๋ฉ์ด์
๊ณผ ํ๋ผ๋ฏธํฐ๋ฅผ ๋ง์ ธ ๋ณผ ์ ์ผํ ์๋ฆฌ๋ค.**\n\n ๋๋ฉด์์๋ ํธ์์ด ์ด ๊ฐ์ ์ค๋ค โ ใ๋์ด 40% ๋ซํ๋คใ๋ ์ฌ์ค์ด ์ด๋์ ๊ฐ ์จ๋ค. ์ ์\n ์ค์๋ ๊ทธ ์ฌ์ค์ ์ฃผ๋ ๊ฒ์ด ์์ด์, ์๋์ง ์์ผ๋ฉด ํ๋ผ๋ฏธํฐ๋ ๊ธฐ๋ณธ๊ฐ์ ๋จธ๋ฌธ ์ฑ ์์\n ์ ์์ง์ธ๋ค. ํฌํฌ๊ฐ ์ ์ฌ๋ผ๊ฐ๋ ๊ฒ์ ์ ์์๊ฐ ใ์ ๋๋๊ตฌ๋ใ๋ก ์ฝ๊ฒ ๋๋ค.\n\n **๋ฏธ๋ฆฌ๋ณด๊ธฐ ๊ฒ์ด์ง ์์ฐ์ ๊ฒ์ด ์๋๋ค.** ์ฌ๊ธฐ์ ๋ฏผ ๊ฐ์ ์ ์ฅ๋์ง ์๋๋ค.\n */\n div[clips] {\n position: absolute;\n right: 8px;\n bottom: 8px;\n display: flex;\n flex-direction: column;\n gap: 6px;\n padding: 8px 10px;\n color: rgba(255, 255, 255, 0.92);\n background-color: rgba(28, 28, 30, 0.72);\n border-radius: 8px;\n font-size: 0.72rem;\n }\n div[clips] label {\n display: grid;\n grid-template-columns: auto 96px 34px;\n align-items: center;\n gap: 8px;\n }\n /*\n ๋ง๋ ์์ ๋๋ ๋จ์ถ. ์์ธ๋ฅผ ๋ง๋ ์๋ฆฌ์ ์์ด์ผ ใ์ง๊ธ ์ด๊ฒ์ ๊ธฐ๋ณธ์ผ๋กใ๊ฐ ์ฝํ๋ค.\n ์ํ ๊ฒ์ด ์์ ๋๋ง ๋์ค๋ฏ๋ก, ๋ ์ ์๋ ์นธ์ด ์๋๋ค.\n */\n div[clips] button[pose] {\n align-self: stretch;\n padding: 4px 8px;\n font: inherit;\n font-size: 0.7rem;\n color: rgba(255, 255, 255, 0.92);\n background-color: rgba(255, 255, 255, 0.14);\n border: 1px solid rgba(255, 255, 255, 0.22);\n border-radius: 5px;\n cursor: pointer;\n }\n div[clips] button[pose]:hover {\n background-color: rgba(255, 255, 255, 0.24);\n }\n div[clips] span[drive] {\n opacity: 0.6;\n font-size: 0.66rem;\n }\n div[clips] input {\n width: 96px;\n accent-color: var(--md-sys-color-primary);\n }\n div[clips] output {\n font-variant-numeric: tabular-nums;\n text-align: right;\n opacity: 0.85;\n }\n\n /* ์ธ์ธ ์ ์๋ ์ํ๋ฅผ ๋น ํ๋ฉด์ผ๋ก ๋์ง ์๋๋ค โ ์ ์ ๋ณด์ด๋์ง ๋งํ๋ค */\n div[cannot] {\n position: absolute;\n inset: 0;\n display: flex;\n align-items: center;\n justify-content: center;\n padding: var(--spacing-large, 12px);\n text-align: center;\n line-height: 1.6;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n background-color: ${unsafeCSS(WORKBENCH)};\n }\n `\n\n /** ์ ์ ์ค์ธ ๊ฒ. ์ ์ฅ ํ์์ผ๋ก ๋ฐ๋๋ค โ ๋๋ฉด์ด ์๋นํ๋ ๊ฒ์ด ์ด ํ์์ด๋ค. */\n @property({ type: Object }) source?: FigureSource\n\n /**\n * ์ ์ ์ค์ธ ์ด์. **๊ธฐ๋ณธ๊ฐ์ด ์ง๊ธ ๋ฌด์์ธ์ง ์๋ ค๊ณ ๋ง ์ฅ๋ค** โ ๊ณ ์น์ง ์๋๋ค.\n *\n * `source` ๋ก๋ ํ๋ผ๋ฏธํฐ๋ฅผ ์ฝ์ ์ ์์ง๋ง, ํ๋ณด๋ฅผ ๋ฏธ๋ฆฌ ๋ณผ ๋๋ `source` ๊ฐ ํ๋ณด์ ๊ฒ์ด๊ณ \n * ์ด์์ ์ด๋ ค ์๋ ๋ํ์ ๊ฒ์ด๋ค. ใ์ด ์์ธ๋ฅผ ๊ธฐ๋ณธ์ผ๋กใ๋ ์ด๋ ค ์๋ ๋ํ์๋ง ๋ป์ด ์๋ค.\n */\n @property({ type: Object }) draft?: FigureDraft\n\n /**\n * ๋ณด๊ธฐ ์ค์ . ์ ์ฅ๋์ง ์๋๋ค(`figure-view.ts`).\n *\n * ํ๋์ ์ด ํ๋ฉด๋ง ์กฐ๋ช
๊ณผ ํ๊ฒฝ์ **ํ๋์ฝ๋ฉ**ํ๋ค. ์ ์์๊ฐ ํ๊ฒฝ ํญ์์ ๋ฌด์์ ๋ฐ๊ฟ๋\n * ํธ์ง ์บ๋ฒ์ค๋ง ๋ฌ๋ผ์ง๊ณ ์ฌ๊ธฐ๋ ๊ทธ๋๋ก์๋ค โ ๋ ํ๋ฉด์ด ๊ฐ์ ๊ฒ์ ๋ค๋ฅด๊ฒ ๋ณด์ฌ ์ฃผ์๋ค.\n */\n @property({ type: Object }) view: ViewSettings = DEFAULT_VIEW\n\n @query('div[stage]') private stage!: HTMLDivElement\n\n /** ์ธ์ธ ์ ์๋ ์ฌ์ . ์์ผ๋ฉด ์ธ์ด ๊ฒ์ด๋ค. */\n @state() private cannot = ''\n\n private scene?: SceneHandle\n /** ์ง๊ธ ์ธ์ ๋ ๊ฒ์ ๊ฐ. ๊ฐ์ผ๋ฉด ๋ค์ ์ธ์ฐ์ง ์๋๋ค. */\n private standing?: string\n private watcher?: ResizeObserver\n\n /** ์ง๊ธ ๋ฏผ clip ๋ฐฐ์. clip ์ด๋ฆ โ ์. **์ ์ฅ๋์ง ์๋๋ค.** */\n @state() private driving: Record<string, number> = {}\n /** ์ง๊ธ ๋ฏผ ํ๋ผ๋ฏธํฐ ๊ฐ. ์ด๋ฆ โ `range` ์ ๋จ์๋ก ์ฐ ์. **์ ์ฅ๋์ง ์๋๋ค.** */\n @state() private giving: Record<string, number> = {}\n\n render() {\n const clips = this.source?.animations ?? []\n const parameters = this.source?.parameters ?? []\n\n return html`\n <div stage></div>\n ${this.cannot\n ? html`<div cannot>${this.cannot}</div>`\n : html`<div legend>\n ${PREVIEW_WAYS.map(way => html`<span>${way.axes.length === 0 ? i18next.t('figure.label.preview-base') : way.name}</span>`)}\n </div>\n ${clips.length + parameters.length > 0 ? this.renderDrivers(clips, parameters) : ''}`}\n `\n }\n\n /**\n * ์์ง์ ํ๋์ ์์ก์ด ํ๋.\n *\n * ๋ ๊ฐ๋๋ฅผ **๋๊ธ์ด ๋ค๋ฅธ ์ฑ๋ก** ๋ธ๋ค. clip ์ ๋ฐฐ์์ด๋ผ 0 ์ด ๋ฉ์ถค์ด๊ณ 0~3 ์ด ๋ป์ด\n * ์์ผ๋ฉฐ, ํ๋ผ๋ฏธํฐ๋ ๋ฌผ๋ฆฌ๋์ด๋ผ ๊ทธ `range` ๊ฐ ๊ณง ๋๊ธ์ด๊ณ ๋จ์๊ฐ ๋ฐ๋ผ ๋ถ๋๋ค. ํ๋์\n * 0~1 ๋ก ๋ญ๋ฑ๊ทธ๋ฆฌ๋ฉด ใ1ใ์ด ๋ฌด์จ ๋ป์ธ์ง ๋งค๋ฒ ํท๊ฐ๋ฆฌ๊ณ , 1200mm ๋ฅผ ๋ฃ์ด ๋ณด๋ ค๋ ์ ์์๊ฐ\n * ๋ฃ์ ์๋ฆฌ๋ฅผ ๋ชป ์ฐพ๋๋ค.\n */\n private renderDrivers(\n clips: NonNullable<FigureSource['animations']>,\n parameters: NonNullable<FigureSource['parameters']>\n ) {\n /*\n ์ง๊ธ ์ธ์ด ์์ธ๋ฅผ ๊ธฐ๋ณธ๊ฐ์ผ๋ก ์ํ๋ ์๋ฆฌ. **๋ง๋ ์์ ๋๋ค** โ ์์ธ๋ฅผ ๋ง๋ ๊ณณ์ด ์ฌ๊ธฐ๋ผ,\n ๊ฐ์ ์ฝ์ด ํ๋ผ๋ฏธํฐ ์นธ์ผ๋ก ์ฎ๊ฒจ ์ ๋ ์๋ณต์ด ์์ด์ง๋ค. ์ํ ๊ฒ์ด ์์ผ๋ฉด ์์ ์ ๋์จ๋ค.\n */\n const changes = poseChanges(this.draft, this.giving)\n\n return html`\n <div clips>\n ${changes.length > 0\n ? html`<button\n pose\n title=${i18next.t('figure.text.pose-as-default-explained')}\n @click=${() => this.poseAsDefault()}\n >\n ${i18next.t('figure.button.pose-as-default')}\n </button>`\n : ''}\n ${parameters.map(parameter => {\n const range = parameter.range\n const value = this.giving[parameter.name] ?? parameter.default ?? range?.min ?? 0\n const step = range ? Math.max((range.max - range.min) / 100, 0.01) : 1\n\n return html`\n <label>\n <span>${parameter.label ?? parameter.name} <span drive>${range?.unit ?? ''}</span></span>\n <input\n type=\"range\"\n min=${range?.min ?? 0}\n max=${range?.max ?? 1}\n step=${step}\n .value=${String(value)}\n @input=${(e: Event) => this.give(parameter.name, Number((e.target as HTMLInputElement).value))}\n />\n <output>${Math.round(value)}</output>\n </label>\n `\n })}\n ${clips.map(clip => {\n const value = this.driving[clip.name] ?? 1\n\n return html`\n <label>\n <span>${clip.name} <span drive>${i18next.t('figure.label.playback-speed')}</span></span>\n <input\n type=\"range\"\n min=\"0\"\n max=\"3\"\n step=\"0.05\"\n .value=${String(value)}\n @input=${(e: Event) => this.drive(clip.name, Number((e.target as HTMLInputElement).value))}\n />\n <output>${value.toFixed(2)}</output>\n </label>\n `\n })}\n </div>\n `\n }\n\n /**\n * ์ธ์ ๋ ์ธ์คํด์ค ์ ๋ถ์ ๊ฐ์ ๊ฐ์ ์ค๋ค.\n *\n * ํ๋๋ง ๋ชฐ๋ฉด ์ธ ๋ฐฐ์จ์ด ์๋ก ๋ค๋ฅธ ์์ธ๋ก ์์, ํฌ๊ธฐ ๋ฐ์์ ๋ณด๋ ค๊ณ ๋๋ํ ๋์ ๋ป์ด\n * ์ฌ๋ผ์ง๋ค.\n */\n private drive(name: string, value: number): void {\n this.driving = { ...this.driving, [name]: value }\n this.tellInstances('clips', this.driving)\n }\n\n /**\n * ํ๋ผ๋ฏธํฐ ๊ฐ์ ์ค๋ค โ **`range` ์ ๋จ์ ๊ทธ๋๋ก๋ค.**\n *\n * 0~1 ๋ก ๋ฐ๊ฟ์ ์ฃผ์ง ์๋๋ค. ๊ทธ ํ์ฐ์ ๋ฐํ์์ ์ผ์ด๊ณ , ์ฌ๊ธฐ์ ํ ๋ฒ ๋ ํ๋ฉด ๋ ๊ณณ์ด\n * ๊ฐ๋ฆด ์ ์๋ค. ์ ์์๊ฐ ํ๋ฉด์์ ๋ณด๋ 1200 ์ด ์ฌ์ ๊ทธ๋๋ก ๊ฐ๋ค.\n */\n private give(name: string, value: number): void {\n this.giving = { ...this.giving, [name]: value }\n this.tellInstances('parameters', this.giving)\n }\n\n /**\n * ์ธ์ด ์์ธ๋ฅผ ๊ธฐ๋ณธ๊ฐ์ผ๋ก โ **์
์ ์ฌ๊ธฐ์ ํ์ง ์๋๋ค.**\n *\n * ์ด์์ ์ฅ๊ณ ์๋ ๊ฒ์ ํ์ด์ง์ด๊ณ , ๋๋๋ฆฌ๊ธฐ์ ใ์ ์ฅ ์ ๋จใ๋ ๊ฑฐ๊ธฐ์ ๋งค๊ธด๋ค. ์ฌ๊ธฐ์\n * ์ด์์ ๋ง๋ค์ด ๋ณด๋ด๋ฉด ๊ทธ ์
์ด ๋ ๊ณณ์ผ๋ก ๊ฐ๋ฆฐ๋ค. ๋ฏผ ๊ฐ๋ง ์ฌ๋ฆฐ๋ค.\n */\n private poseAsDefault(): void {\n this.dispatchEvent(\n new CustomEvent('pose-as-default', { detail: { values: { ...this.giving } }, bubbles: true, composed: true })\n )\n }\n\n private tellInstances(key: 'clips' | 'parameters', values: Record<string, number>): void {\n for (const component of this.scene?.root?.components ?? []) {\n component.set?.(key, { ...values })\n }\n }\n\n /**\n * ๋ณด๊ธฐ ์ค์ ์ด ๋ฐ๋๋ฉด **๋ค์ ์ธ์ฐ์ง ์๊ณ ์ฌ์ ๋ฃ๋๋ค** โ ๋ ๊ฐ๋ง ๋นผ๊ณ .\n *\n * ์กฐ๋ช
ยทํ๊ฒฝยท๋ฐํ์ ์ฌ์ด ์ค์ค๋ก ๋ฐ์ํ๋ค(`three-capability` ์ `onchange`). ์ฌ๋ผ์ด๋๋ฅผ\n * ๋๋ ๋์ ๋ค์ ์ธ์ฐ๋ฉด ์นด๋ฉ๋ผ๊ฐ ๋งค ํ๋ ์ ์ฒ์์ผ๋ก ๋์๊ฐ๋ค.\n *\n * ์ขํ ๊ธฐ์ค๊ณผ ์ฒ์ฅ ๋์ด๋ ๋ค๋ฅด๋ค. ์ฌ์ด ๊ทธ ๋๋ก ์ธ์คํด์ค ๋์ด๋ฅผ ์ ํ๋๋ฐ, ๊ทธ ๊ณ์ฐ์ ์ธ์ธ\n * ๋ ํ ๋ฒ ๋๋ค โ ์ด๋ฏธ ์ธ์ ๋ ๊ฒ์ ๋ฃ์ด ๋ด์ผ ์๋ฆฌ๊ฐ ์ ๋ฐ๋๋ค. ๊ทธ๊ฒ๋ง ๋ค์ ์ธ์ด๋ค.\n */\n willUpdate(changed: Map<string, unknown>) {\n if (!this.hasUpdated) return\n\n if (changed.has('source')) {\n this.standUp()\n return\n }\n\n if (!changed.has('view')) return\n\n const before = changed.get('view') as ViewSettings | undefined\n const now = this.view ?? DEFAULT_VIEW\n if (before?.placement !== now.placement || before?.ceilingHeight !== now.ceilingHeight) {\n this.standUp()\n return\n }\n\n this.scene?.root?.set?.(sceneLook(now))\n }\n\n firstUpdated() {\n this.standUp()\n this.watcher = new ResizeObserver(() => this.scene?.resize?.())\n this.watcher.observe(this)\n }\n\n disconnectedCallback() {\n super.disconnectedCallback()\n this.watcher?.disconnect()\n this.watcher = undefined\n this.teardown()\n }\n\n /**\n * ์ ์ํ ๊ฒ์ ์ปดํ์ผํด ์ธ์ด๋ค.\n *\n * **ํ์์ ์ด๊ฒผ์ผ๋ฉด ์ธ์ฐ์ง ์๋๋ค.** ๋ฐ์ฏค ์ธ์ด ๊ฒ์ ๋ณด์ฌ ์ฃผ๋ฉด ๋ฌด์์ด ์๋ชป๋๋์ง ์ ์\n * ์๋ค. ํ์ ํจ๋์ด ์ด๋ฏธ ์ฌ์ ๋ฅผ ๋งํ๊ณ ์์ผ๋ฏ๋ก ์ฌ๊ธฐ์๋ ์ธ์ธ ์ ์๋ค๊ณ ๋ง ํ๋ค.\n */\n private standUp() {\n const source = this.source\n if (!source || source.parts.length === 0) {\n this.cannot = i18next.t('figure.text.preview-needs-a-part')\n this.teardown()\n return\n }\n\n const view = this.view ?? DEFAULT_VIEW\n /* ์ฌ์ด ์ด ๋๋ก ์ธ์คํด์ค ๋์ด๋ฅผ ์ ํ๋ค โ ์๋ช
์ ์ ๋ฃ์ผ๋ฉด ๋ค์ ์ธ์๋ ๊ทธ๋๋ก ์ ๋ค. */\n const signature = JSON.stringify([source, view.placement, view.ceilingHeight])\n if (this.scene && this.standing === signature) return\n\n const { errors } = validate(source)\n if (errors.length > 0) {\n this.cannot = i18next.t('figure.text.preview-blocked-by-errors')\n this.teardown()\n return\n }\n\n this.teardown()\n // ํ๋ณธ์ด ๋ฐ๋๋ฉด ๋ฏผ ๊ฐ๋ ์ฒ์์ผ๋ก ๋๋ฆฐ๋ค โ ๋ค๋ฅธ ์์ฐ์ clip ์ด๋ฆ์ด ๋จ์ผ๋ฉด ์ ๋๋ค.\n this.driving = {}\n\n try {\n registerFigure(compile(source) as never)\n\n /*\n ๋๋ฉด์ด ํ๋ ์ผ์ ๊ทธ๋๋ก ํ๋ค. ์ปดํฌ๋ํธ์๋ ํ์
์ด๋ฆ๊ณผ ์๋ฆฌยทํฌ๊ธฐ๋ง ์ ๋๋ค โ\n ์ฒญ์ฌ์ง๋ ์๋ณธ๋ ๋๋ฉด์ ๋ค์ด๊ฐ์ง ์๋๋ค.\n\n ๊ฐ์ฅ ํฐ ๊ฒ์ด ๋ค์ด๊ฐ ๋งํผ ํ์ ์ก๊ณ , ์ธ๋ก๋ก ์ค์ ๋๋ ๋๋ํ ๋๋๋ค.\n */\n const { base } = source\n const biggest = PREVIEW_FACTOR\n /** ์ด ์กฐํฉ์์ ์ถ๋ณ ๋ฐฐ์จ. ์กฐํฉ์ ๋ ์ถ๋ง ํค์ด๋ค. */\n const growth = (way: (typeof PREVIEW_WAYS)[number]) => ({\n x: way.axes.includes('x') ? PREVIEW_FACTOR : 1,\n y: way.axes.includes('y') ? PREVIEW_FACTOR : 1,\n z: way.axes.includes('z') ? PREVIEW_FACTOR : 1\n })\n // ์ฌ๋ฐฑ์ ๋๋ํ ๋๋ฉด ํ๋ฉด์์ ํ์์ด ์์์ง๋ค. ๊ฐ์ฅ ํฐ ๊ฒ์ด ๊ฒจ์ฐ ๋ค์ด๊ฐ ๋งํผ๋ง ์ก๋๋ค.\n /** ๋ค ์นธ์ฉ ๋ ์ค. */\n const COLUMNS = 4\n const cell = { x: base.x * biggest * 1.25, z: base.z * biggest * 1.25 }\n const rows = Math.ceil(PREVIEW_WAYS.length / COLUMNS)\n /*\n ์ฌ์ ๋ฑ๋ง์ด ํ์๊ณผ ๋ค๋ฅด๋ค โ `width` ๊ฐ ํ์์ x, `height` ๊ฐ z, `depth` ๊ฐ y ๋ค.\n ์ฎ๊ธฐ๋ ์ผ์ ์ฌ๊ธฐ ํ ์ค์ ๋ชจ์ ๋๋ค.\n\n `depth` ๋ฅผ ๋ ์ ๋ ์ด์ ๊ฐ ์๋ค. ์ ์ ์ผ๋ฉด ํ๋ฉด ๋ ์ถ์ ๊ธฐํํ๊ท ์ผ๋ก ์กํ์,\n ใy ๋ง ํค์ด๋คใ๊ฐ xยทz ๋ฅผ ์ ๊ฑด๋๋ฆฌ๋๋ฐ๋ ๋์ด๊ฐ ์ ์ค๋ฅธ๋ค.\n\n ๋์ด๋ **๋ฐฐ์น ๊ธฐ์ค์ด ์ ํ๋ค.** ๋ฐ๋ฅ ๊ธฐ๋ฐ์ ๋
์์ ์ฌ๋ผ์ค๊ณ , ์ฒ์ ๊ธฐ๋ฐ์ ์ฒ์ฅ์\n ๋ถ์ด ๋ด๋ ค์จ๋ค. ์ฌ๋์ ๋๋ํ ์ธ์ฐ๋ ์๋ฆฌ๋ผ ์ด๊ฒ์ด ๋์ ๋ฐ๋ก ๋ณด์ธ๋ค โ ๋ฐ๋ฅ ๊ธฐ๋ฐ์ด๋ฉด\n ๋ฐ๋ฉด์ด, ์ฒ์ ๊ธฐ๋ฐ์ด๋ฉด ์๋ฉด์ด ํ ์ค์ด ๋๋ค.\n */\n const components = PREVIEW_WAYS.map((way, at) => {\n const grow = growth(way)\n const column = at % COLUMNS\n const row = Math.floor(at / COLUMNS)\n const width = Math.round(base.x * grow.x)\n const height = Math.round(base.z * grow.z)\n const tall = Math.round(base.y * grow.y)\n\n return {\n type: source.type,\n id: `at-${way.name}`,\n // ์นธ ๊ฐ์ด๋ฐ์ ๋๋๋ค โ ํฌ๊ธฐ๊ฐ ์ ๋ง๋ค ๋ฌ๋ผ ์ผ์ชฝ์ ๋ง์ถ๋ฉด ์ค์ด ์ ์ฝํ๋ค.\n left: Math.round(column * cell.x + (cell.x - width) / 2),\n top: Math.round(row * cell.z + (cell.z - height) / 2),\n width,\n height,\n depth: tall\n }\n })\n\n const draft = {\n width: Math.round(cell.x * COLUMNS),\n height: Math.round(cell.z * rows),\n /*\n ํ์ ๋์ด๋ ๊ฐ์ฅ ํฐ ์ธ์คํด์ค๋ฅผ ๋ด์์ผ ํ๋ค. ์ ์ฃผ๋ฉด ์นด๋ฉ๋ผ๊ฐ ํ๋ฉด๋ง ๋ณด๊ณ ์๋ฆฌ๋ฅผ\n ์ก์์, ํค๊ฐ ํฐ ๋ชจ๋ธ์ ๋ฐ๋๋ง ๋ณด์ธ๋ค โ ์๊ทธ๋ํ์๋ฅผ 2 ๋ฐฐ๋ก ๋์ผ๋ฉด 2200 ์ธ๋ฐ ํ์ด\n ๊ทธ๊ฒ์ ๋ชจ๋ฅด๋ฉด ๋ฐ์นจ๋ง ํ๋ฉด์ ๋ ๋ค.\n\n ์ด๋์ ์ฌ๋ ค ๋์์ง๋ **์ฌ์ด ์ ํ๋ฏ๋ก**(`FigureRealObject.effectiveZPos`), ์ฌ๊ธฐ์๋\n ์ด๋ ๊ฒฝ์ฐ์๋ ๋ด๊ธฐ๋ ๊ฒฝ๊ณ๋ง ์ก๋๋ค. ๋ฐ๋ฅ ๊ธฐ๋ฐ์ ๊ฐ์ฅ ํฐ ๊ฒ์ ํค๊น์ง, ์ฒ์ ๊ธฐ๋ฐ์\n ์ฒ์ฅ๊น์ง๋ค. ๋ฐฐ์น๋ฅผ ๋์ด๋ก ์ฎ๊ธฐ๋ ๊ณ์ฐ์ ์ฌ๊ธฐ์ ๋ค์ ์ฐ๋ฉด ๊ทธ๊ฒ์ด ๋ ๋ฒ์งธ๊ฐ ๋๋ค.\n */\n depth: previewBoardDepth(source, view.ceilingHeight, biggest)\n }\n\n this.scene = create({\n target: this.stage,\n model: {\n type: 'model-layer',\n width: draft.width,\n height: draft.height,\n depth: draft.depth,\n threed: true,\n sky: 'color',\n /*\n ๋ณด๊ธฐ ์ค์ ์ ๊ทธ๋๋ก ์ฃ๋๋ค.\n\n ์ฌ๊ธฐ๋ง ์กฐ๋ช
ยทํ๊ฒฝยท๋ฐํ์ ํ๋์ฝ๋ฉํ๊ณ ์์๋ค. ์ ์์๊ฐ ํ๊ฒฝ ํญ์์ ์กฐ๋ช
์\n ์ฌ๋ ค๋ ํธ์ง ์บ๋ฒ์ค๋ง ๋ฐ์์ง๊ณ ์ด ํ๋ฉด์ ๊ทธ๋๋ก์ฌ์, ๊ฐ์ ๊ฒ์ ๋ ํ๋ฉด์ด\n ๋ค๋ฅด๊ฒ ๋ณด์ฌ ์ฃผ์๋ค.\n\n `sceneLook` ์ด ์ขํ ๊ธฐ์ค๊ณผ ์ฒ์ฅ ๋์ด๋ฅผ ๋นผ๊ณ ์ค๋ค โ ์ฌ์ด ์๋ ์ด๋ฆ์ด ์๋๊ฑฐ๋\n (`ceilingHeight`) ํธ์ง ์บ๋ฒ์ค์ ์๋ฉด ์ ๋๋ ๊ฒ(`placement`)์ด๋ผ์๋ค. ๋ ๋ค ์๋์\n ์ฌ์ ๋ฑ๋ง๋ก ๋ฐ๋ก ์ฃ๋๋ค.\n */\n ...sceneLook(view),\n placement: view.placement,\n /*\n ๋ถ์ฐฉ๋ฉด์ ๋์ด. ์ฌ์ด ์ด ์๋ฆฌ๋ฅผ ๊ฐ๊ณ (`real-object.ts` ์ `sceneHeights`), ์ฒ์ ๊ธฐ๋ฐ\n ๋ํ์ด ์ฌ๊ธฐ์ ์ ๋์ด๋ฅผ ์ป๋๋ค. ๋๋ฉด์์๋ ํ์ฅ์ด ์ด ๊ฐ์ ์ค๋ค.\n */\n heights: { floor: 0, ceiling: view.ceilingHeight },\n pixelRatio: Math.min(3, (window.devicePixelRatio || 1) * 2),\n components\n },\n // ๋ณด๊ธฐ๋ง ํ๋ ์๋ฆฌ๋ค. ์ง๊ฑฐ๋ ๋ ์ ์์ด์ผ ํ๋ค.\n mode: 0\n }) as SceneHandle\n\n this.standing = signature\n this.scene.resize?.()\n this.scene.fit?.('ratio')\n this.scene.root?.fitCameraToModel?.()\n this.cannot = ''\n } catch (e) {\n // ์์ธ์ ์ง์ด๋ด์ง ์๋๋ค โ ๋์ง ๋ง์ ๊ทธ๋๋ก ๋ณด์ฌ ์ค๋ค.\n this.cannot = (e as Error).message\n }\n }\n\n private teardown() {\n this.scene?.dispose?.()\n this.scene = undefined\n this.standing = undefined\n }\n}\n"]}
|
|
@@ -65,8 +65,9 @@ export declare class FigureReport extends FigureReport_base {
|
|
|
65
65
|
* ์ง์ ๋ตํ์ง ์๋๋ค โ ํ์์ด ์ ์ธ๋ ํ๋ ์์ธ์ง๋ฅผ ๋งํ ๋ฟ์ด๋ค. ๊ทธ๋์ ๊ฐ์๋ฅผ
|
|
66
66
|
* ๋จธ๋ฆฌ์ ์ฌ๋ฆฌ๊ณ ๋ฑ๊ธ์ ์์ badge ๋ก ๋ด๋ฆฐ๋ค.
|
|
67
67
|
*
|
|
68
|
-
* ๊ทผ๊ฑฐ๋ฅผ ํจ๊ป ๋ธ๋ค.
|
|
69
|
-
*
|
|
68
|
+
* ๊ทผ๊ฑฐ๋ฅผ ํจ๊ป ๋ธ๋ค. ๋ฌถ์์ผ๋ก ๊ฐ๋ฆฌ๋ ๊ฐ์์ ๋ถ๋ชจ๋ **์ค์ธก**์ด๊ณ (2026-09-18, Apple M5), ์ฐ
|
|
69
|
+
* ๊ธฐ๊ณ์ ๋ ์ง๋ฅผ ํจ๊ป ์ ๋๋ค โ ์ ์ง ์์ผ๋ฉด ์ด๋์๋ ์ฐธ์ธ ์๋ก ์ฝํ๋ค. ์ผ๊ฐํ ์ชฝ์ ์์ง ์ค๊ณ
|
|
70
|
+
* ๋ฌธ์์ ๋ชฉํ์น๋ผ ๊ทธ๋ ๋ค๊ณ ์ ๋๋ค.
|
|
70
71
|
*/
|
|
71
72
|
private renderVerdict;
|
|
72
73
|
/**
|
|
@@ -6,7 +6,7 @@ import { unsafeSVG } from 'lit/directives/unsafe-svg.js';
|
|
|
6
6
|
import { i18next, localize } from '@operato/i18n';
|
|
7
7
|
import { ScrollbarStyles } from '@operato/styles';
|
|
8
8
|
import { blocksRelease, compile, costCurveSvg, costOf, scoreOf, sizingReport, validate } from '@hatiolab/figure-model';
|
|
9
|
-
import { capacityOf } from './scene-budget.js';
|
|
9
|
+
import { capacityOf, MEASURED } from './scene-budget.js';
|
|
10
10
|
import { maturityOf } from './maturity.js';
|
|
11
11
|
/**
|
|
12
12
|
* ํ๋จ ํจ๋. ๋ชจ๋ธ๋ฌ ํ๋ฉด์ **๋ ๋ ์๋ค.**
|
|
@@ -488,8 +488,9 @@ let FigureReport = class FigureReport extends localize(i18next)(LitElement) {
|
|
|
488
488
|
* ์ง์ ๋ตํ์ง ์๋๋ค โ ํ์์ด ์ ์ธ๋ ํ๋ ์์ธ์ง๋ฅผ ๋งํ ๋ฟ์ด๋ค. ๊ทธ๋์ ๊ฐ์๋ฅผ
|
|
489
489
|
* ๋จธ๋ฆฌ์ ์ฌ๋ฆฌ๊ณ ๋ฑ๊ธ์ ์์ badge ๋ก ๋ด๋ฆฐ๋ค.
|
|
490
490
|
*
|
|
491
|
-
* ๊ทผ๊ฑฐ๋ฅผ ํจ๊ป ๋ธ๋ค.
|
|
492
|
-
*
|
|
491
|
+
* ๊ทผ๊ฑฐ๋ฅผ ํจ๊ป ๋ธ๋ค. ๋ฌถ์์ผ๋ก ๊ฐ๋ฆฌ๋ ๊ฐ์์ ๋ถ๋ชจ๋ **์ค์ธก**์ด๊ณ (2026-09-18, Apple M5), ์ฐ
|
|
492
|
+
* ๊ธฐ๊ณ์ ๋ ์ง๋ฅผ ํจ๊ป ์ ๋๋ค โ ์ ์ง ์์ผ๋ฉด ์ด๋์๋ ์ฐธ์ธ ์๋ก ์ฝํ๋ค. ์ผ๊ฐํ ์ชฝ์ ์์ง ์ค๊ณ
|
|
493
|
+
* ๋ฌธ์์ ๋ชฉํ์น๋ผ ๊ทธ๋ ๋ค๊ณ ์ ๋๋ค.
|
|
493
494
|
*/
|
|
494
495
|
renderVerdict() {
|
|
495
496
|
const score = this.score;
|
|
@@ -525,7 +526,11 @@ let FigureReport = class FigureReport extends localize(i18next)(LitElement) {
|
|
|
525
526
|
per: capacity.per.toLocaleString(),
|
|
526
527
|
budget: capacity.budget.toLocaleString()
|
|
527
528
|
})}
|
|
528
|
-
<em
|
|
529
|
+
<em>
|
|
530
|
+
${capacity.bound === 'groups'
|
|
531
|
+
? i18next.t('figure.text.budget-measured-on', { gpu: MEASURED.gpu, on: MEASURED.on })
|
|
532
|
+
: i18next.t('figure.text.budget-not-measured-yet')}
|
|
533
|
+
</em>
|
|
529
534
|
</p>
|
|
530
535
|
</section>
|
|
531
536
|
`;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"figure-report.js","sourceRoot":"","sources":["../../client/modeller/figure-report.ts"],"names":[],"mappings":"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","sourcesContent":["import '@material/web/icon/icon.js'\n\nimport { css, html, LitElement, nothing, svg } from 'lit'\nimport { customElement, property, state } from 'lit/decorators.js'\nimport { unsafeSVG } from 'lit/directives/unsafe-svg.js'\n\nimport { i18next, localize } from '@operato/i18n'\nimport { ScrollbarStyles } from '@operato/styles'\nimport { blocksRelease, compile, costCurveSvg, costOf, scoreOf, sizingReport, validate } from '@hatiolab/figure-model'\nimport type { FigureCost, FigureScore, FigureSource } from '@hatiolab/figure-model'\n\nimport { capacityOf } from './scene-budget.js'\nimport { maturityOf } from './maturity.js'\nimport type { MaturityAxis } from './maturity.js'\nimport type { FigureCapacity } from './scene-budget.js'\n\n/**\n * ํ๋จ ํจ๋. ๋ชจ๋ธ๋ฌ ํ๋ฉด์ **๋ ๋ ์๋ค.**\n *\n * ์ ์ฅ์ ์ ํํด์ผ ์๋ ๊ฒ์ด ์๋๋ค. ๋ถํ์ ํ๋ ๋์ ๋๋ง๋ค ๋ฌด๊ฒ์ ์ ์๊ฐ ์์ง์ด๊ณ ,\n * ๊ทธ๊ฒ์ด ๋ณด์ฌ์ผ ์ ์์๊ฐ ๊ณ ์น ์ ์๋ค. ใ๋ฌด์ ๋๋ฌธ์ ์ ์๊ฐ ๋ฎ์๊ฐใ๋ฅผ ๋งํด ์ฃผ์ง\n * ์์ผ๋ฉด ์ ์๋ ์์๋ฆฌ์ผ ๋ฟ์ด๋ค.\n *\n * ## ์
์ ์ฌ๊ธฐ์ ํ์ง ์๋๋ค\n *\n * ๊ฒ์ฆยท์๊ฐยท์ ์๋ ์ ๋ถ `@hatiolab/figure-model` ์ด ํ๋ค. ํ๋ฉด์ **๋ถ๋ฅด๊ณ ๋ณด์ฌ ์ค\n * ๋ฟ**์ด๋ค. ํ๋๋ ๋ฑ๊ธ ๊ฒฝ๊ณ๋ฅผ ํ๋ฉด์ด ๋ค์ ์ ํ๋ฉด ์๋ฒ๊ฐ ๊ฑฐ์ ํ ๊ฒ์ ํ๋ฉด์ด\n * ํต๊ณผ์ํค๊ฒ ๋๋ค.\n */\n@customElement('figure-report')\nexport class FigureReport extends localize(i18next)(LitElement) {\n static styles = [\n ScrollbarStyles,\n css`\n :host {\n display: flex;\n flex-direction: column;\n overflow-y: auto;\n background-color: var(--md-sys-color-surface-container-lowest);\n border-left: 1px solid var(--md-sys-color-outline-variant);\n color: var(--md-sys-color-on-surface);\n font: var(--label-font, inherit);\n /*\n ์ด ํจ๋์ ๋ณธ๋ฌธ ํฌ๊ธฐ๋ฅผ ์ฌ๊ธฐ์ ํ ๋ฒ ์ ํ๋ค.\n\n ์ ์๋ ๊ท์น๋ง๋ค ๋ฐ๋ก ์ ์๋ค. ๊ทธ๋ฌ๋ฉด ๋น ๋จ๋ฆฐ ๊ท์น์ด ๋ณธ๋ฌธ ๊ธฐ๋ณธ ํฌ๊ธฐ(1rem)๋ฅผ\n ๋ฌผ๋ ค๋ฐ์ ๊ทธ ์ค๋ง ์ ๋ชฉ์ฒ๋ผ ์ปค์ง๋ค. ์ค๋ฅ๊ฐ ์๋๋ผ์ ํ๋ฉด์ ๋์ ๋ด์ผ ์๋ค.\n ์ด ํ์ผ์์๋ง ๋ ๋ฒ ๋ฌ๋ค.\n\n form ์์(input ยท select ยท button)๋ ๊ธ๊ผด์ ๋ฌผ๋ ค๋ฐ์ง ์์ผ๋ฏ๋ก ๊ฐ์ ์ ์ด์ผ ํ๋ค.\n ๊ทธ๊ฒ ๋ง๊ณ ๋ ์ฌ๊ธฐ ๊ฐ์ ๋ฐ๋ฅธ๋ค.\n */\n font-size: 0.76rem;\n }\n\n section {\n padding: var(--spacing-medium, 8px) var(--spacing-large, 12px);\n border-bottom: 1px solid var(--md-sys-color-outline-variant);\n }\n section > h3 {\n margin: 0 0 6px 0;\n font-size: var(--ui-t-micro, 11px);\n font-weight: 700;\n letter-spacing: 0.04em;\n text-transform: uppercase;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n\n /* โโ ๋ช ๊ฐ๊น์ง ํธํ๊ฐ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ\n ๋ก์ฐํด๋ฆฌ์ ๊ฐ์ ใ์ผ๋ง๋ ๋ง์ด ํธํ๊ฒ ๋์ ์ ์๋ใ๋ค. ๊ทธ ๋ต์ด ๋จธ๋ฆฌ์ ์จ๋ค.\n ๋ฑ๊ธ์ ํ์ ์์ฒด๊ฐ ํ๋ ์์ธ์ง๋ฅผ ๋งํ ๋ฟ์ด๋ผ ์์ ์์ badge ๋ก ๋๋ค. */\n div[verdict] {\n display: flex;\n align-items: baseline;\n gap: 6px;\n }\n span[capacity] {\n font-size: 2.1rem;\n font-weight: 800;\n line-height: 1;\n letter-spacing: -0.01em;\n color: var(--md-sys-color-primary);\n }\n span[unit] {\n font-size: 0.9rem;\n font-weight: 600;\n color: var(--md-sys-color-primary);\n }\n /*\n ๋ฑ๊ธ badge.\n\n ์ ์๋ \"C 0\" ๋ง ์์๋ค. ๊ธ์ ํ๋์ ์ซ์ ํ๋์ธ๋ฐ ์ด๋์๋ ๋ป์ด ์์ด์, ํฌ๊ฒ ๋ฌ\n ๊ฐ์ ์์ ๋นจ๊ฐ badge ๊ฐ ๋ถ์ ๊ฒ์ผ๋ก๋ง ์ฝํ๋ค. 0 ์ 100์ ๋ง์ ์ 0 ์ ์ผ๋ก ์ฝ๋ ๊ฒ์ด\n ์์ฐ์ค๋ฝ๋ค. ์ค์ ๋ป์ \"์ ์ธํ ํ๋์ ๋จ์ ์ฌ์ ๊ฐ 0\" ์ด๋ค.\n\n ๊ทธ๋์ ๋ฌด์์ ์ธก์ ํ๋์ง๋ฅผ badge ์์ ์ ๊ณ , ๋๊ธ์ ๋ฐ๋ก ์๋ ์ค์ ๋ ๋ณด์ด๊ฒ ๋๋ค.\n */\n span[grade] {\n display: flex;\n align-items: baseline;\n gap: 5px;\n margin-left: auto;\n padding: 3px 10px;\n font-size: 0.76rem;\n font-weight: 700;\n color: var(--md-sys-color-on-primary-container);\n background-color: var(--md-sys-color-primary-container);\n border-radius: 999em;\n }\n span[grade] small {\n font-size: 0.68rem;\n font-weight: 500;\n }\n /*\n C ๋ ํ๋๋ฅผ ์งํจ ๊ฒ์ด๋ค. ๋นจ๊ฐ์ ๋๊ธด ๊ฒ(D)์๋ง ์ด๋ค. ์งํจ ๊ฒ์ ๋นจ๊ฐ์ ์ฐ๋ฉด\n ๊ณ ์น ๊ฒ์ด ์๋๋ฐ๋ ๊ณ ์ณ์ผ ํ ๊ฒ์ฒ๋ผ ๋ณด์ธ๋ค.\n */\n span[grade][tight] {\n color: var(--md-sys-color-on-tertiary-container, #3d2f00);\n background-color: var(--md-sys-color-tertiary-container, #ffdf9a);\n }\n /*\n Pair the container with its on-container.\n\n This used to fill with --md-sys-color-error and write with\n --md-sys-color-on-error-container. Once the palette made containers\n neutral and moved the meaning into the text colour, those two became the\n same red and the badge went blank -- a filled pill with no readable text.\n */\n span[grade][over] {\n color: var(--md-sys-color-on-error-container);\n background-color: var(--md-sys-color-error-container);\n }\n\n /* ๋ฑ๊ธ ๋๊ธ. ์ ์ด ๋์ง ์๋๋ค โ ํ ๋ฒ ๋ณด๊ณ ๋ง๋ ๊ฐ์ด ์๋๋ผ ๋ณผ ๋๋ง๋ค ํ์ํ๋ค */\n p[scale] {\n display: flex;\n flex-wrap: wrap;\n gap: 2px 10px;\n margin: 6px 0 0 0;\n font-size: 0.7rem;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n p[scale] b {\n font-weight: 700;\n }\n p[scale] span[now] b {\n color: var(--md-sys-color-primary);\n }\n p[scale] span[now] {\n color: var(--md-sys-color-on-surface);\n }\n /* ์ด ํฐ ์ซ์๊ฐ ์ด๋ ์ถ์ธ์ง ๋จผ์ ๋งํ๋ค โ ์ฑ์๋์ ํ ์ถ์ด์ง ์ ๋ถ๊ฐ ์๋๋ค */\n p[lead] {\n margin: 0 0 4px 0;\n font-size: 0.74rem;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n\n /* ๊ทผ๊ฑฐ๋ฅผ ํจ๊ป ๋ธ๋ค โ ์ซ์๋ง ํฌ๊ฒ ๋ด๊ฑธ๋ฉด ์ฌ ๋ณธ ๊ฐ์ฒ๋ผ ์ฝํ๋ค */\n p[basis] {\n margin: 6px 0 0 0;\n font-size: 0.72rem;\n line-height: 1.55;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n p[basis] em {\n font-style: normal;\n color: var(--md-sys-color-tertiary);\n }\n span[score] {\n font-size: 0.8rem;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n\n /* ๋ฌด์ ๋๋ฌธ์ ์ด ๋ฑ๊ธ์ธ๊ฐ โ ํ๋์ ๊ฐ์ฅ ๊ฐ๊น์ด ํญ๋ชฉ */\n p[because] {\n margin: 8px 0 0 0;\n /* ๋ณธ๋ฌธ ํฌ๊ธฐ๋ฅผ ๋ฌผ๋ ค๋ฐ์ผ๋ฉด ์ด ์ค๋ง ์ ๋ชฉ์ฒ๋ผ ์ปค์ง๋ค โ ํ๋ฉด์ ๋์ ๋ณด๊ณ ์์๋ค */\n font-size: 0.78rem;\n line-height: 1.6;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n p[because] strong {\n color: var(--md-sys-color-on-surface);\n }\n\n /* โโ ์ฑ์๋ radar โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ\n ์ฌ์ฏ ์ถ์ ํ ๊ทธ๋ฆผ์ผ๋ก. ๋ชฉ๋ก๋ง ๋๋ฉด ใ์ด๋ ์ชฝ์ด ๋ชจ์๋๊ฐใ๊ฐ ์ ๋ณด์ธ๋ค.\n ๋ชป ์ฐ ์ถ์ ์ ์ ์ฐ์ง ์๊ณ ์ด๋ง ํ๋ฆฌ๊ฒ ๋จ๊ธด๋ค โ 0 ์ผ๋ก ์ฐ์ผ๋ฉด ใ๋์๋คใ๊ฐ ๋๋ค. */\n div[radar] {\n display: flex;\n justify-content: center;\n padding: 2px 0 6px 0;\n color: var(--md-sys-color-primary);\n }\n div[radar] svg {\n width: 100%;\n max-width: 240px;\n height: auto;\n }\n div[radar] polygon[web] {\n fill: none;\n stroke: var(--md-sys-color-outline-variant);\n stroke-width: 0.6;\n }\n div[radar] line[spoke] {\n stroke: var(--md-sys-color-outline-variant);\n stroke-width: 0.6;\n }\n div[radar] polygon[shape] {\n fill: color-mix(in srgb, var(--md-sys-color-primary) 22%, transparent);\n stroke: var(--md-sys-color-primary);\n stroke-width: 1.4;\n stroke-linejoin: round;\n }\n div[radar] circle[dot] {\n fill: var(--md-sys-color-primary);\n }\n div[radar] text {\n font-size: 5.2px;\n fill: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n\n /* ๊ทธ๋ฆผ์ ์๋ฆฌ๋ฅผ ์ฃผ์ง ์์ ์ถ์ ๊ธ๋ก ๋ฐํ๋ค */\n p[unmeasured] {\n margin: 0 0 8px 0;\n font-size: 0.7rem;\n line-height: 1.5;\n color: var(--md-sys-color-tertiary);\n }\n\n /* โโ ์ฑ์๋ ์ถ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ\n ํ ์ซ์๋ก ํฉ์น์ง ์๋๋ค. ํฉ์น๋ฉด ใ๋ฌด์์ ๊ณ ์ณ์ผ ํ๋ใ๊ฐ ์ฌ๋ผ์ง๋ค. */\n ul[axes] {\n margin: 0;\n padding: 0;\n list-style: none;\n display: flex;\n flex-direction: column;\n gap: 7px;\n }\n ul[axes] li {\n display: grid;\n grid-template-columns: 1fr auto;\n gap: 2px 8px;\n font-size: 0.75rem;\n }\n ul[axes] li[blocked] {\n opacity: 0.7;\n }\n ul[axes] em {\n grid-column: 1 / -1;\n font-style: normal;\n font-size: 0.68rem;\n line-height: 1.5;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n /* ๋ชป ์ฐ ์ถ์ 0 ์ผ๋ก ๋์ง ์๋๋ค โ 0 ์ ใ๋์๋คใ๋ ๋ป์ด ๋์ด ๋ฒ๋ฆฐ๋ค */\n ul[axes] li[blocked] em {\n color: var(--md-sys-color-tertiary);\n }\n span[reading] {\n font-family: var(--mono-font, monospace);\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n\n /* โโ ์์ฐ ๋ง๋ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ */\n ul[budgets] {\n margin: 0;\n padding: 0;\n list-style: none;\n display: flex;\n flex-direction: column;\n gap: 6px;\n }\n ul[budgets] li {\n display: grid;\n grid-template-columns: 1fr auto;\n gap: 2px 8px;\n font-size: 0.75rem;\n }\n div[bar] {\n grid-column: 1 / -1;\n height: 4px;\n background-color: var(--md-sys-color-surface-container-highest);\n border-radius: 2px;\n overflow: hidden;\n }\n div[bar] > i {\n display: block;\n height: 100%;\n background-color: var(--md-sys-color-primary);\n }\n div[bar] > i[tight] {\n background-color: var(--md-sys-color-error);\n }\n\n /* โโ ๋ฌด๊ฒ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ */\n dl[metrics] {\n margin: 0;\n display: grid;\n grid-template-columns: 1fr auto;\n gap: 4px 8px;\n font-size: 0.78rem;\n }\n dl[metrics] dt {\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n dl[metrics] dd {\n margin: 0;\n text-align: right;\n font-family: var(--mono-font, monospace);\n }\n\n /* โโ ์ถ์ด โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ\n ๊ทธ๋ฆผ์ ์์ฐ ํฌ๊ธฐ๊ฐ 680px ๋ค. 300px ์นธ์ ๋ฃ์ผ๋ฉด ๊ธ์๊ฐ 4px ์ด ๋์ด ์๋ฌด๊ฒ๋\n ์ฝ์ ์ ์๋ค โ ์ฌ์ด๋๋ฐ์๋ ์ซ์๋ฅผ ๋๊ณ , ๊ทธ๋ฆผ์ ์ ํํด์ ํฌ๊ฒ ๋ณธ๋ค. */\n button[expand] {\n margin-top: 6px;\n padding: 4px 10px;\n font: var(--label-font, inherit);\n font-size: 0.74rem;\n color: var(--md-sys-color-on-surface);\n background: none;\n border: 1px solid var(--md-sys-color-outline-variant);\n border-radius: 6px;\n cursor: pointer;\n }\n button[expand]:hover {\n background-color: var(--md-sys-color-surface-container);\n }\n\n div[sheet] {\n position: fixed;\n inset: 0;\n z-index: 10;\n display: flex;\n align-items: center;\n justify-content: center;\n padding: var(--spacing-large, 12px);\n background-color: rgba(0, 0, 0, 0.32);\n }\n div[sheet] > figure {\n max-width: 100%;\n max-height: 100%;\n margin: 0;\n padding: var(--spacing-large, 12px);\n overflow: auto;\n color: var(--md-sys-color-primary);\n background-color: var(--md-sys-color-surface-container-lowest);\n /* ๋ด๋ ๋ฉด์ด ํ์
์ด๋ฉด ์์ชฝ ๋ชจ์๋ฆฌ๋ ์์ฝ์ด๋ค โ ์ํธ ์์ฒด๋ ํ์ด์ง ๊ฐ์ ์ด๋ค */\n border-radius: 6px;\n box-shadow: 0 8px 32px rgba(0, 0, 0, 0.28);\n }\n div[sheet] svg {\n display: block;\n /* ์์ฐ ํฌ๊ธฐ๋ณด๋ค ์๊ฒ ์ค์ด์ง ์๋๋ค โ ์ข์ผ๋ฉด ๋๊ฒจ ๋ณด๊ฒ ๋๋ค */\n min-width: 680px;\n }\n div[sheet] figcaption {\n display: flex;\n align-items: center;\n justify-content: flex-end;\n }\n div[sheet] button[close] {\n padding: 5px 14px;\n font: var(--label-font, inherit);\n color: var(--md-sys-color-on-surface);\n background: none;\n border: 1px solid var(--md-sys-color-outline-variant);\n border-radius: 999em;\n cursor: pointer;\n }\n\n /* โโ ์๋ฆผ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ */\n ul[findings] {\n margin: 0;\n padding: 0;\n list-style: none;\n display: flex;\n flex-direction: column;\n gap: 6px;\n }\n ul[findings] li {\n display: flex;\n gap: 6px;\n line-height: 1.5;\n }\n ul[findings] md-icon {\n --md-icon-size: 16px;\n flex: none;\n color: var(--md-sys-color-error);\n }\n ul[findings] li[violation] md-icon {\n color: var(--md-sys-color-tertiary);\n }\n /* ์ด๊ธด ์๋ฆฌ. ๋ฌธ๊ตฌ์ ๋ถ์ด ํ๋ฅด๋ฉด ๋ฌธ์ฅ์ ์ผ๋ถ๋ก ์ฝํ๋ค โ badge ๋ก ๋ณด์ด๊ฒ ๋๋ค */\n code[at] {\n padding: 1px 5px;\n font-family: var(--mono-font, monospace);\n font-size: 0.68rem;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n background-color: var(--md-sys-color-surface-container);\n border-radius: 4px;\n white-space: nowrap;\n }\n\n /*\n ๋ฐ๊ฒฌ์ด ์์ ๋์ ๋ฌธ๊ตฌ.\n\n ํฌ๊ธฐ๋ฅผ ์ ์ ์ด ๋์๋๋ ๋ณธ๋ฌธ ๊ธฐ๋ณธ ํฌ๊ธฐ๋ฅผ ๋ฌผ๋ ค๋ฐ์ ์ด ์ค๋ง ์ ๋ชฉ์ฒ๋ผ ์ปค์ก๋ค. ์ด\n ํจ๋์ ๊ธ์๋ ์ ๋ถ 0.7rem ๋์ธ๋ฐ ์ฌ๊ธฐ๋ง 1rem ์ด๋ผ ์๋์ชฝ์ด ๋ฌด๋์ ธ ๋ณด์๋ค.\n\n ์ฐพ์ ๊ฒ์ด ์์ ๋์ ๋ชฉ๋ก(ul[findings] li)๊ณผ ๊ฐ์ ํฌ๊ธฐ๋ก ๋ง์ถ๋ค. ์์ ๋์ ์์ ๋\n ์ ์ ์๊น์๊ฐ ๋ฌ๋ผ์ง ์ด์ ๊ฐ ์๋ค.\n\n ์ด ํ์ผ์์ ๊ฐ์ ์ค์๋ฅผ ๋ ๋ฒ์งธ๋ก ํ๋ค. p[because] ์๋ ๊ฐ์ ์ฃผ์์ด ์๋ค.\n */\n p[quiet] {\n margin: 0;\n font-size: 0.76rem;\n line-height: 1.6;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n `\n ]\n\n /** ์ ์ ์ค์ธ ์๋ณธ ๋ฐ์ดํฐ. ๋ฐ๋๋ฉด ๋ค์ ์ธก์ ํ๋ค. */\n @property({ type: Object }) source?: FigureSource\n\n @state() private cost?: FigureCost\n @state() private score?: FigureScore\n @state() private curve = ''\n /** 1๋ง ๊ฐ๋ฅผ ๋์์ ๋. ์ ์์๊ฐ ์ค์ ๋ก ๊ถ๊ธํ ์ซ์๋ค. */\n @state() private many?: FigureCost\n /** ๋ช ๊ฐ๊น์ง ๋์ ์ ์๋. ์ด ํจ๋์ ๋จธ๋ฆฌ๋ค. */\n @state() private capacity?: FigureCapacity\n /** ์ถ์ด ๊ทธ๋ฆผ์ ์ ํฌ๊ธฐ๋ก ํผ์ณค๋. */\n @state() private expanded = false\n @state() private errors: { code: string; message: string; at?: string }[] = []\n /**\n * ํ์์ด ๊ถํ์ง ์๋ ๊ฒ โ **๊ทธ์ค ๋์ ๋ฐํ์ ๋ง๋๋ค.**\n *\n * ๋ฑ๊ธ์ ํ์์์ ๋ฐ๋๋ค(`blocksRelease`). ํ๋ฉด์ด ์ ๋ชฉ๋ก์ ๋ค๋ฉด ํ์์ ์ฝ๋๊ฐ ํ๋ ๋ ๋\n * ์กฐ์ฉํ ใ์๋ฆผใ์ผ๋ก ๊ทธ๋ ค์ง๊ณ , ์ ์์๋ ๋ฐํ์ด ๋งํ ๊ฒ์ **๋๋ฌ ๋ณด๊ณ ๋์์ผ** ์๋ค.\n *\n * `actual` ์ ์ผ๋ง๋ ๋์ณค๋๋ค. ใ์์๋ฅผ ๋ฒ์ด๋๋คใ๋ง์ผ๋ก๋ 2mm ์ธ์ง 250mm ์ธ์ง ๋ชจ๋ฅด๊ณ ,\n * ๊ทธ ๋์ ๊ณ ์น๋ ํ์ด ๋ค๋ฅด๋ค.\n */\n @state() private violations: { code: string; message: string; blocking: boolean; actual?: number }[] = []\n /**\n * ํฌ๊ธฐ๋ฅผ ๋ฐ๊ฟ ๋ดค์ ๋ ๊ฐ๋ผ์ง๋๊ฐ โ **๋ฐํ์ ๋ง๋ ๊ฒ**์ด๋ค.\n *\n * ์ด๋ ฅ ํญ์ด ๊ฐ์ ํ์ ์ ์๋ฒ์์ ๋ฐ์ ๋ฐํ ๋ฌธ์ ์ ๊ทธ์ง๋ง, ๊ทธ๊ฒ์ **์ ์ฅ๋ ์ ๋ณธ**์ ๋ํ\n * ๊ฒ์ด๋ผ ์ ์ฅํ๊ธฐ ์ ์๋ ๋ตํ์ง ๋ชปํ๋ค. ์ฌ๊ธฐ์๋ ์ ์ ์ค์ธ ์ ๋ณธ์ ๊ทธ๋๋ก ์ฌ๋ฏ๋ก, ๋ถํ์\n * ์ฎ๊ธฐ๋ ๊ทธ ์๋ฆฌ์์ ๊ฐ๋ผ์ง์ด ์๊ฒผ๋์ง ์ฌ๋ผ์ก๋์ง ๋ณด์ธ๋ค โ ์ ์ฅํ๊ณ ํญ์ ์ฎ๊ฒจ ํ์ธํ๊ฒ\n * ๋๋ฉด ๊ณ ์น ๋๊ฐ ์ด๋ฏธ ์ง๋ ์๋ค.\n */\n @state() private sizing: { code: string; message: string; at?: string; blocking: boolean }[] = []\n /**\n * ์์ง ๋ถํ์ด ํ๋๋ ์๋ โ **์ ์ ์ ์ด์ง ํ์์ ์ด๊ธด ๊ฒ์ด ์๋๋ค.**\n *\n * ํ์์ ๋ถํ 0๊ฐ๋ฅผ ์ค๋ฅ๋ก ๋ณธ๋ค(`missing-parts`). ๋ฐํ ๊ด์ ์์๋ ๋ง๋ค. ๊ทธ๋ฐ๋ฐ ์๋ก ๋ง๋ค๊ธฐ๋ฅผ\n * ๋๋ฅธ ์งํ๊ฐ ๋ฐ๋ก ๊ทธ ์ํ์ด๋ฏ๋ก, ๊ทธ๊ฒ์ ๊ทธ๋๋ก ์ค๋ฅ๋ก ๊ทธ๋ฆฌ๋ฉด **์๋ฌด๊ฒ๋ ํ์ง ์์๋๋ฐ ๋ถ์\n * ํ๋ฉด**์ ๋ณด๊ฒ ๋๋ค. ๊ทธ๋์ ์ด ์๋ฆฌ์์ ๋์ ๊ฐ๋ฅธ๋ค.\n */\n @state() private bare = false\n\n willUpdate(changed: Map<string, unknown>) {\n if (changed.has('source')) {\n this.measure()\n }\n }\n\n render() {\n /*\n ๋ถํ์ด ์์ผ๋ฉด ์ด ์๋ฆฌ๋ **ํ์ ์ด ์๋๋ผ ์๋ด**๋ค. ์ด๋ฏธ ์๋ ใ๋ถํ์ ์ถ๊ฐํ๋ฉด ๋์ต๋๋คใ๊ฐ\n ์ ํํ ๊ทธ ๋ง์ด๋ฏ๋ก ๊ทธ๊ฒ์ ์ด๋ค โ ๊ฐ์ ์ํ์ ๋ฌธ์ฅ์ ๋ ๋์ง ์๋๋ค.\n\n ์๋ ์
๋ค(๋จธ๋ฆฌยท์ถยทํ๋ยท์ถ์ด)์ ๋ถํ์ด ์์ด์ผ ๋ป์ด ์๊ณ , ์ฌ์ง ์์ ๊ฐ์ ๋ค๊ณ ๊ทธ๋ฆฌ๋ฉด 0 ์ผ๋ก\n ๋ณด์ธ๋ค. 0 ์ ใ๋์๋คใ๋ก ์ฝํ๋ฏ๋ก ๊ทธ ์๋ฆฌ์ ๋์ง ์๋๋ค.\n */\n if (!this.source || this.bare) {\n return html`\n <section>\n <p quiet>${i18next.t('figure.text.report-appears-when-you-add-a-part')}</p>\n </section>\n `\n }\n\n // ํ์์ ์ด๊ธด ์ํ์์๋ ์
์ด ๋ป์ ๊ฐ์ง ๋ชปํ๋ค โ ๋ฌด์์ด ์๋ชป๋๋์ง๋ง ๋ณด์ฌ ์ค๋ค.\n if (this.errors.length > 0) {\n return html`${this.renderFindings()}`\n }\n\n return html`\n ${this.renderVerdict()} ${this.renderAxes()} ${this.renderBudgets()} ${this.renderMetrics()} ${this.renderCurve()}\n ${this.renderFindings()} ${this.renderSheet()}\n `\n }\n\n /**\n * ๋จธ๋ฆฌ โ ๋ช ๊ฐ๊น์ง ํธํ๊ฐ.\n *\n * ๋ก์ฐํด๋ฆฌ์ ๊ฐ์ ใ์ผ๋ง๋ ๋ง์ด ํธํ๊ฒ ๋์ ์ ์๋ใ์ ์๋ค. ๋ฑ๊ธ B ๋ ๊ทธ ๋ฌผ์์\n * ์ง์ ๋ตํ์ง ์๋๋ค โ ํ์์ด ์ ์ธ๋ ํ๋ ์์ธ์ง๋ฅผ ๋งํ ๋ฟ์ด๋ค. ๊ทธ๋์ ๊ฐ์๋ฅผ\n * ๋จธ๋ฆฌ์ ์ฌ๋ฆฌ๊ณ ๋ฑ๊ธ์ ์์ badge ๋ก ๋ด๋ฆฐ๋ค.\n *\n * ๊ทผ๊ฑฐ๋ฅผ ํจ๊ป ๋ธ๋ค. ์ด ๊ฐ์์ ๋ถ๋ชจ๋ ์ค์ธก์ด ์๋๋ผ ์ค๊ณ ๋ฌธ์์ ๋ชฉํ์น์ด๊ณ (๋ฏธ๊ฒฐ\n * D-20), ๊ทธ ์ฌ์ค์ด ํ๋ฉด์ ์์ผ๋ฉด ์ฌ ๋ณธ ๊ฐ์ฒ๋ผ ์ฝํ๋ค.\n */\n private renderVerdict() {\n const score = this.score\n const capacity = this.capacity\n if (!score || !capacity) return nothing\n\n return html`\n <section>\n <h3>${i18next.t('figure.label.maturity')}</h3>\n <p lead>${i18next.t('figure.label.axis-scale')} โ ${i18next.t('figure.text.how-many-fit')}</p>\n <div verdict>\n <span capacity>${capacity.instances.toLocaleString()}</span>\n <span unit>${i18next.t('figure.text.instances-unit')}</span>\n <span\n grade\n ?tight=${score.grade === 'C'}\n ?over=${score.grade === 'D'}\n title=${i18next.t('figure.text.grade-explained')}\n >\n ${score.grade}\n <small>${i18next.t('figure.text.headroom-percent', { percent: Math.round(score.score) })}</small>\n </span>\n </div>\n <p because>\n ${i18next.t('figure.text.grade-decided-by')}\n <strong>${i18next.t('figure.label.budget-' + score.tightest.key)}</strong>\n โ ${score.tightest.used} / ${score.tightest.limit}\n (${Math.round((score.tightest.used / score.tightest.limit) * 100)}%)\n </p>\n ${this.renderGradeScale(score.grade)}\n <p basis>\n ${i18next.t('figure.text.bound-by-' + capacity.bound, {\n per: capacity.per.toLocaleString(),\n budget: capacity.budget.toLocaleString()\n })}\n <em>${i18next.t('figure.text.budget-not-measured-yet')}</em>\n </p>\n </section>\n `\n }\n\n /**\n * ๋ฑ๊ธ ๋๊ธ.\n *\n * AยทBยทCยทD ๊ฐ ๋ฌด์์ ๋ปํ๋์ง ํ๋ฉด ์ด๋์๋ ์์๋ค. badge ๋ง ๋ณด๊ณ ๋ ์ข์์ง ๋์์ง๋,\n * ๋ฌด์์ ๊ณ ์ณ์ผ ์ค๋ฅด๋์ง๋ ์ ์ ์๋ค. ๋๊ธ์ ๋ ๊ณ์ ๋๊ณ ์ง๊ธ ์ด๋์ ์๋์ง๋ฅผ\n * ํ์ํ๋ค.\n *\n * ์ ์ด ๋์ง ์๋๋ค. ํ ๋ฒ ๋ฐฐ์ฐ๊ณ ๋ง๋ ๊ฐ์ด ์๋๋ผ ๋ณผ ๋๋ง๋ค ๋์กฐํ๋ ๊ฐ์ด๋ค.\n */\n private renderGradeScale(now: string) {\n const bounds: [string, string][] = [\n ['A', 'โค 50%'],\n ['B', 'โค 75%'],\n ['C', 'โค 100%'],\n ['D', '> 100%']\n ]\n\n return html`\n <p scale>\n <span>${i18next.t('figure.text.grade-scale-lead')}</span>\n ${bounds.map(\n ([grade, bound]) => html`<span ?now=${grade === now}><b>${grade}</b> ${bound}</span>`\n )}\n </p>\n `\n }\n\n /**\n * ์ฑ์๋ โ ์ฌ๋ฌ ์ถ์ผ๋ก ๋ณธ๋ค.\n *\n * ใ๋ช ๊ฐ๊น์ง ํธํ๊ฐใ ํ๋๋ก๋ ์ข์ ํ์๊ณผ ๋์ ํ์์ด ๊ตฌ๋ถ๋์ง ์๋๋ค. ๋ถํ ํ๋์ง๋ฆฌ\n * ์์๋ ๊ทธ ์ถ์์๋ ๋ง์ ์ด๋ค.\n *\n * **๋ชป ์ฌ๋ ์ถ์ 0 ์ผ๋ก ๋์ง ์๋๋ค.** 0 ์ ใ๋์๋คใ๋ ๋ป์ด ๋๋๋ฐ, ์ฌ์ค์ ์์ง\n * ์ธก์ ํ ๋ฐฉ๋ฒ์ด ์๋ ๊ฒ์ด๋ค. ์ธก์ ํ์ง ๋ชปํ๋ค๊ณ ์๋ฆฌ๊ณ ์ด์ ๋ฅผ ๋ถ์ธ๋ค. ์ง์ด๋ธ ์ ์๋ณด๋ค ๊ทธ๊ฒ์ด\n * ์ด ๋ฆฌํฌํธ๋ฅผ ๋ฏฟ์ ๋งํ๊ฒ ๋ง๋ ๋ค.\n */\n private renderAxes() {\n if (!this.cost || !this.score || !this.source) return nothing\n\n /*\n ๊ท๋ชจ๋ ๋ชฉ๋ก์์ ๋บ๋ค โ ๋จธ๋ฆฌ๋ก ์ฌ๋ผ๊ฐ๋ค. ๊ฐ์ ์ซ์๋ฅผ ๋ ๋ฒ ๋ด๋ฉด ์ฝ๋ ์ฌ๋์ด\n ๋์ด ๋ค๋ฅธ ๊ฒ์ธ ์ค ์๋ค.\n */\n const axes = maturityOf(this.source, this.cost, this.score).filter(axis => axis.key !== 'scale')\n\n // radar ์๋ ์ฌ์ฏ์ ๋ค ๊ทธ๋ฆฐ๋ค. ๊ท๋ชจ๊ฐ ์ด๋์ฏค์ธ์ง ํจ๊ป ๋ณด์ฌ์ผ ๋ป์ด ์๋ค\n const all = maturityOf(this.source, this.cost, this.score)\n\n return html`\n <section>\n <h3>${i18next.t('figure.label.by-axis')}</h3>\n <div radar>${this.renderRadar(all.filter(axis => axis.ratio !== undefined))}</div>\n ${this.renderUnmeasured(all.filter(axis => axis.ratio === undefined))}\n <ul axes>\n ${axes.map(axis => this.renderAxis(axis))}\n </ul>\n </section>\n `\n }\n\n /**\n * ์ฑ์๋ radar. **์ธก์ ํ ์ถ๋ง ๊ทธ๋ฆฐ๋ค.**\n *\n * ์ธก์ ํ์ง ๋ชปํ๋ ์ถ๋ spoke ๋ฅผ ๊ทธ๋ ค ๋๊ณ ๋ํ๋ง ๊ฑด๋๋ฐ๋ ๋๊ฐ ์์๋ค. ๊ทธ๋ฌ๋ฉด ๊ทธ ๋ฐฉํฅ์ ๊ฐ๋ก์ง๋ฅด๋\n * ์ง์ ์ด ์๊ฒจ์ ๋ํ์ด ๊ทธ์ชฝ์ผ๋ก ์ํน ๋ค์ด๊ฐ ๊ฒ์ฒ๋ผ ๋ณด์ธ๋ค. 0 ์ผ๋ก ์ฐ์ง ์์ผ๋ ค๊ณ ํ\n * ์ผ์ธ๋ฐ ๊ฒฐ๊ณผ๋ 0 ์ผ๋ก ์ฐ์ ๊ฒ๊ณผ ๋๊ฐ์ด ์ฝํ๋ค. ์ ์ ์ด๊ณผ ๋ฌผ์ํ๋ก๋ ๊ทธ ์ธ์์ด\n * ์ง์์ง์ง ์์๋ค.\n *\n * ๊ทธ๋์ ์์ ๋นผ๊ณ , ๋ชป ์ฌ๋ ์ถ์ ๊ทธ๋ฆผ ์๋์ ๊ธ๋ก ์ ๋๋ค. ์ด ์ ์๋ ๊ฒ์ ๊ทธ๋ฆผ์\n * ์๋ฆฌ๋ฅผ ์ฃผ์ง ์๋ ํธ์ด ์ ์งํ๋ค.\n */\n private renderRadar(axes: MaturityAxis[]) {\n // ๊ทธ๋ฆผ ์์์๋ **์งง์ ์ด๋ฆ**์ ์ด๋ค. ๊ธด ์ด๋ฆ์ ๊ทธ๋๋ก ์ฐ๋ฉด ์ผ์ชฝ์ด ์๋ฆฐ๋ค โ\n // ํ๋ฉด์ ๋์ ๋ณด๊ณ ์์๋ค.\n const cx = 60\n const cy = 46\n const r = 28\n\n const at = (index: number, ratio: number) => {\n const angle = -Math.PI / 2 + (index * 2 * Math.PI) / axes.length\n return [cx + r * ratio * Math.cos(angle), cy + r * ratio * Math.sin(angle)]\n }\n\n const points = axes\n .map((axis, index) => at(index, Math.max(0.04, Math.min(1, axis.ratio ?? 0))).map(n => n.toFixed(1)).join(','))\n .join(' ')\n\n return svg`\n <svg viewBox=\"0 0 120 96\" aria-hidden=\"true\">\n ${[0.33, 0.66, 1].map(\n ring => svg`<polygon web points=${axes.map((_, i) => at(i, ring).map(n => n.toFixed(1)).join(',')).join(' ')}></polygon>`\n )}\n ${axes.map((_, index) => {\n const [x, y] = at(index, 1)\n return svg`<line spoke x1=${cx} y1=${cy} x2=${x.toFixed(1)} y2=${y.toFixed(1)}></line>`\n })}\n <polygon shape points=${points}></polygon>\n ${axes.map((axis, index) => {\n const [x, y] = at(index, Math.max(0.04, Math.min(1, axis.ratio ?? 0)))\n return svg`<circle dot cx=${x.toFixed(1)} cy=${y.toFixed(1)} r=\"1.4\"></circle>`\n })}\n ${axes.map((axis, index) => {\n const [x, y] = at(index, 1.28)\n const anchor = x < cx - 3 ? 'end' : x > cx + 3 ? 'start' : 'middle'\n return svg`\n <text x=${x.toFixed(1)} y=${(y + 1.8).toFixed(1)} text-anchor=${anchor}>\n ${i18next.t('figure.label.axis-' + axis.key + '-short')}\n </text>\n `\n })}\n </svg>\n `\n }\n\n /**\n * ๊ทธ๋ฆผ์ ์๋ ์ถ์ ๊ธ๋ก ๋ฐํ๋ค.\n *\n * ๋นผ๊ธฐ๋ง ํ๋ฉด ์ถ์ด ์ฌ์ฏ์ธ์ง ๋ค์ฏ์ธ์ง ์ ์ ์๊ณ , ์๋ ๊ฒ์ ์๋ค๊ณ ๋งํ์ง ์์ ์
์ด\n * ๋๋ค. ๋ฌด์์ ์์ง ๋ชป ์ฌ๋์ง ํ ์ค๋ก ์ ๋๋ค. ์ ๋ชป ์ฌ๋์ง๋ ์๋ ๋ชฉ๋ก์ ๊ทธ ํญ๋ชฉ์\n * ๊ทธ๋๋ก ์๋ค.\n */\n private renderUnmeasured(axes: MaturityAxis[]) {\n if (axes.length === 0) return nothing\n\n return html`\n <p unmeasured>\n ${i18next.t('figure.text.axes-not-measurable-yet', {\n axes: axes.map(axis => i18next.t('figure.label.axis-' + axis.key)).join(' ยท ')\n })}\n </p>\n `\n }\n\n private renderAxis(axis: MaturityAxis) {\n const name = i18next.t('figure.label.axis-' + axis.key)\n\n if (axis.blocked) {\n return html`\n <li blocked>\n <span>${name}</span>\n <span reading>${i18next.t('figure.text.not-measurable-yet')}</span>\n <em>${i18next.t(axis.blocked)}</em>\n </li>\n `\n }\n\n const ratio = Math.max(0, Math.min(1, axis.ratio ?? 0))\n return html`\n <li>\n <span>${name}</span>\n <span reading>${axis.readingKey ? i18next.t(axis.readingKey) : (axis.reading ?? '')}</span>\n <div bar><i style=\"width:${Math.round(ratio * 100)}%\"></i></div>\n ${axis.because ? html`<em>${i18next.t(axis.because)}</em>` : ''}\n </li>\n `\n }\n\n /**\n * ์์ฐ ๋ง๋.\n *\n * ์ซ์๋ง ๋์ด๋์ผ๋ฉด ์ด๋ ๊ฒ์ด ๊ฝ ์ฐผ๋์ง ๋์ ์ ๋ค์ด์จ๋ค. ํ๋์ ๊ฐ์ฅ ๊ฐ๊น์ด ํ๋๋ฅผ ์์ผ๋ก\n * ๊ตฌ๋ถํ๋ค. ๊ทธ๊ฒ์ด ์ ์๋ฅผ ์ ํ ํญ๋ชฉ์ด๋ค.\n *\n * ## `use.label` ์ ์ฐ์ง ์๋ ์ด์ \n *\n * `FigureBudgetUse` ์ `label` ๊ณผ `why` ๊ฐ ์๊ณ ใ์ ์์์๊ฒ ๊ทธ๋๋ก ๋ณด์ฌ ์ค๋คใ๊ณ \n * ์ ํ ์๋ค. ๊ทธ๋ฐ๋ฐ ๊ทธ ๋ฌธ๊ตฌ๊ฐ **ํ๊ตญ์ด๋ก ๊ตฌ์์ ธ** ์๋ค. ์ด ์ ํ์ 5์ธ์ด๋ฅผ ์ฐ๋ฏ๋ก\n * ๊ทธ๊ฒ์ ๊ทธ๋๋ก ์ค์ผ๋ฉด ๋ค๋ฅธ ์ธ์ด ์ฌ์ฉ์์๊ฒ ํ๊ตญ์ด๊ฐ ๋์จ๋ค.\n *\n * `budgets` ๋ **๋ฐฐ์ด**์ด๋ค. `Object.entries` ๋ก ๋๋ฉด ํค๊ฐ ์ธ๋ฑ์ค(0ยท1ยท2โฆ)๊ฐ ๋์ด\n * `figure.label.budget-0` ๊ฐ์ ์๋ ํค๋ฅผ ์ฐพ๋๋ค โ ํ๋ฉด์ ๋์ ๋ณด๊ณ ์์ผ ๋๋ฌ๋ฌ๋ค.\n * ๋ฐฐ์ด์ ๊ทธ๋๋ก ๋๊ณ `use.key` ๋ฅผ ์ด๋ค.\n *\n * ๊ทธ๋์ **์์ ๋ `key`** ๋ก ์ด ํ๋ฉด์ i18n ์ ์ฐพ๋๋ค. `key` ๋ ์ด๊ฑฐํ์ด๋ผ ํ์์\n * ์ผ๋ถ์ด๊ณ , ๋ฌธ๊ตฌ๋ ํ๋ฉด์ ๋ชซ์ด๋ค. figure-model ์ด ๋ฌธ๊ตฌ๋ฅผ ์ธ์ด ์ค๋ฆฝ์ผ๋ก ๋ฐ๊พธ๋ฉด\n * ๊ทธ๋ `label` ์ ์ธ ์ ์๋ค.\n */\n private renderBudgets() {\n const score = this.score\n if (!score) return nothing\n\n return html`\n <section>\n <h3>${i18next.t('figure.label.budgets')}</h3>\n <ul budgets>\n ${score.budgets.map(use => {\n const ratio = Math.min(1, use.ratio)\n const tight = use.key === score.tightest.key\n return html`\n <li>\n <span>${i18next.t('figure.label.budget-' + use.key)}</span>\n <span>${use.used} / ${use.limit}</span>\n <div bar><i ?tight=${tight} style=\"width:${Math.round(ratio * 100)}%\"></i></div>\n </li>\n `\n })}\n </ul>\n </section>\n `\n }\n\n private renderMetrics() {\n const cost = this.cost\n if (!cost) return nothing\n\n return html`\n <section>\n <h3>${i18next.t('figure.label.weight')}</h3>\n <dl metrics>\n <dt>${i18next.t('figure.label.triangles')}</dt>\n <dd>${cost.triangles.toLocaleString()}</dd>\n\n <dt>${i18next.t('figure.label.triangles-at-100')}</dt>\n <dd>${cost.at.triangles.toLocaleString()}</dd>\n\n <dt>${i18next.t('figure.label.draw-calls-at-100')}</dt>\n <dd>${cost.at.drawCalls.toLocaleString()}</dd>\n\n <dt>${i18next.t('figure.label.distinct-shapes')}</dt>\n <dd>${cost.distinctShapes}</dd>\n\n <dt>${i18next.t('figure.label.distinct-materials')}</dt>\n <dd>${cost.distinctMaterials}</dd>\n </dl>\n </section>\n `\n }\n\n /**\n * ์ฌํ์ฉ ์ถ์ด โ ใ๋ง์ด ๋์ผ๋ฉด ์ด๋ป๊ฒ ๋๋ใ์ ๋ตํ๋ค.\n *\n * ## ๊ทธ๋ฆผ์ ์ฌ์ด๋๋ฐ์ ๋ฐ์ด ๋ฃ์ง ์๋๋ค\n *\n * `costCurveSvg` ์ ์์ฐ ํฌ๊ธฐ๋ 680x380 ์ด๊ณ ๊ธ์๊ฐ 11px ๋ค. 300px ์นธ์์\n * width:100% ๋ก ์ค์ด๋ฉด ๊ธ์๊ฐ 4px ์ด ๋์ด **์๋ฌด๊ฒ๋ ์ฝ์ ์ ์๋ค** โ ํ๋ฉด์ ๋์\n * ๋ณด๊ณ ์์ผ ๋๋ฌ๋ฌ๋ค. ์ฝ์ ์ ์๋ ๊ทธ๋ฆผ์ ์๋ ๊ฒ๊ณผ ๊ฐ์ผ๋ฏ๋ก, ์ฌ์ด๋๋ฐ์๋ ์ ์์๊ฐ\n * ์ค์ ๋ก ๊ถ๊ธํ ์ซ์(1๋ง ๊ฐ์ผ ๋)๋ฅผ ๋๊ณ ๊ทธ๋ฆผ์ ์ ํํด์ ์ ํฌ๊ธฐ๋ก ๋ณธ๋ค.\n */\n private renderCurve() {\n const many = this.many\n if (!many && !this.curve) return nothing\n\n return html`\n <section>\n <h3>${i18next.t('figure.label.reuse-trend')}</h3>\n ${many\n ? html`\n <dl metrics>\n <dt>${i18next.t('figure.label.triangles-at-10k')}</dt>\n <dd>${many.at.triangles.toLocaleString()}</dd>\n\n <dt>${i18next.t('figure.label.draw-calls-at-10k')}</dt>\n <dd>${many.at.drawCalls.toLocaleString()}</dd>\n </dl>\n `\n : nothing}\n ${this.curve\n ? html`\n <button expand @click=${() => (this.expanded = true)}>\n ${i18next.t('figure.button.see-the-trend-chart')}\n </button>\n `\n : nothing}\n </section>\n `\n }\n\n /** ๊ทธ๋ฆผ์ ์ ํฌ๊ธฐ๋ก ๋ณด์ฌ ์ค๋ค. ์ข์ผ๋ฉด ์ค์ด์ง ์๊ณ ๋๊ฒจ ๋ณด๊ฒ ๋๋ค. */\n private renderSheet() {\n if (!this.expanded || !this.curve) return nothing\n\n return html`\n <div sheet @click=${() => (this.expanded = false)}>\n <figure @click=${(e: Event) => e.stopPropagation()}>\n ${unsafeSVG(this.curve)}\n <figcaption>\n <button close @click=${() => (this.expanded = false)}>${i18next.t('figure.button.close')}</button>\n </figcaption>\n </figure>\n </div>\n `\n }\n\n /**\n * ๋ฐ๊ฒฌ.\n *\n * ์ค๋ฅ(๋ง๋ ๊ฒ)์ ์๋ฐ(์๋ฆฌ๋ ๊ฒ)์ **๊ฐ๋ ค์** ๋ณด์ฌ ์ค๋ค. ์์ผ๋ฉด ์ ์์๊ฐ ๋ฌด์์\n * ๋ฐ๋์ ๊ณ ์ณ์ผ ํ๋์ง ๋ชจ๋ฅธ๋ค. ์๋ฌด๊ฒ๋ ์์ผ๋ฉด ใ์๋คใ๊ณ ๋งํ๋ค โ ๋น ์๋ฆฌ๋ก ๋๋ฉด\n * ๊ฒ์ฌ๊ฐ ๋์๋์ง ์ ์ ์๋ค.\n */\n private renderFindings() {\n if (this.errors.length === 0 && this.violations.length === 0 && this.sizing.length === 0) {\n return html`\n <section>\n <h3>${i18next.t('figure.label.findings')}</h3>\n <p quiet>${i18next.t('figure.text.no-findings')}</p>\n </section>\n `\n }\n\n return html`\n <section>\n <h3>${i18next.t('figure.label.findings')}</h3>\n <ul findings>\n ${this.sizing.map(\n finding => html`\n <li ?violation=${!finding.blocking}>\n <md-icon>call_split</md-icon>\n <span>${finding.message} ${finding.at ? html`<code at>${finding.at}</code>` : ''}</span>\n </li>\n `\n )}\n ${this.errors.map(\n e => html`\n <li>\n <md-icon>error</md-icon>\n <span>${e.message} ${e.at ? html`<code at>${e.at}</code>` : ''}</span>\n </li>\n `\n )}\n ${this.violations.map(\n v => html`\n <li ?violation=${!v.blocking}>\n <md-icon>${v.blocking ? 'block' : 'info'}</md-icon>\n <span>\n ${v.message}${v.blocking && v.actual !== undefined\n ? html` <code at>${v.actual}</code>`\n : ''}\n </span>\n </li>\n `\n )}\n </ul>\n </section>\n `\n }\n\n /** ์๋ณธ ๋ฐ์ดํฐ๋ฅผ ์ธก์ ํด ๊ฒฐ๊ณผ๋ฅผ ์ํ์ ๋ด๋๋ค. ์
์ ์ ๋ถ figure-model ์ด ํ๋ค. */\n private measure() {\n const source = this.source\n if (!source) {\n this.cost = undefined\n this.score = undefined\n this.many = undefined\n this.capacity = undefined\n this.curve = ''\n this.errors = []\n this.violations = []\n this.sizing = []\n return\n }\n\n /*\n ๋ถํ์ด ์์ผ๋ฉด ํ์ ์ ์์ ํ์ง ์๋๋ค โ ์ด ๊ฒ์ด ์๋ค. ใ๋ฌด์์ ๊ณ ์ณ์ผ ํ๋ใ๊ฐ ์๋๋ผ\n ใ๋ฌด์๋ถํฐ ๋๋ใ์ธ ์ํ์ด๊ณ , ๊ทธ ์๋ด๋ ๋ถํ ๋ชฉ๋ก์ด ์ด๋ฏธ ํ๊ณ ์๋ค.\n */\n this.bare = !source.parts?.length\n if (this.bare) {\n this.cost = undefined\n this.score = undefined\n this.many = undefined\n this.capacity = undefined\n this.curve = ''\n this.errors = []\n this.violations = []\n this.sizing = []\n return\n }\n\n const result = validate(source)\n this.errors = result.errors.map(e => ({ code: e.code, message: e.message, at: e.path }))\n this.violations = result.violations.map(v => ({\n code: v.code,\n message: v.message,\n blocking: blocksRelease(v.code),\n actual: v.actual\n }))\n\n if (this.errors.length > 0) {\n // ํ์์ ์ด๊ฒผ์ผ๋ฉด ์ปดํ์ผ์ด ๋์ง๋ค. ์
์ ๋น์ฐ๊ณ ์ค๋ฅ๋ง ๋ณด์ฌ ์ค๋ค.\n this.cost = undefined\n this.score = undefined\n this.many = undefined\n this.capacity = undefined\n this.curve = ''\n this.sizing = []\n this.dispatchEvent(\n new CustomEvent('verdict-changed', { detail: {}, bubbles: true, composed: true })\n )\n return\n }\n\n const blueprint = compile(source)\n\n /*\n ํฌ๊ธฐ๋ฅผ ๋ฐ๊ฟ ๋ณด๋ ์ผ๊ณฑ ์กฐํฉ. ํ์ ๊ท์น์ `figure-model` ์ `gate.ts` ๊ฐ ์ ํ ๊ฒ์ ๊ทธ๋๋ก\n ์ด๋ค โ ๋ฌด์์ด ๋ง๋ ๊ฒ์ธ์ง ํ๋ฉด์ด ๋ค์ ์ ํ๋ฉด ์๋ฒ์ ๋ค๋ฅธ ๋ง์ ํ๊ฒ ๋๋ค.\n */\n const report = sizingReport(blueprint)\n this.sizing = report.findings.map(finding => ({\n code: finding.code,\n message: finding.message,\n /* ์ซ์๊ฐ ์๋๋ผ ์๋ฆฌ๋ฅผ ๋งํ๋ค โ ๊ฐ๋ผ์ ธ ๋์จ ๋ถํ ์ด๋ฆ์ด ๊ณ ์น ์๋ฆฌ๋ค. */\n at: finding.clumps.map(clump => [...clump].sort().join('+')).join(' | ') || undefined,\n blocking: finding.code === 'sizing-splits'\n }))\n\n this.cost = costOf(blueprint, 100)\n // 1๋ง ๊ฐ๋ figure-model ์ ๋ค์ ๋ฌป๋๋ค โ ํ๋ฉด์ด ๊ณฑ์
์ผ๋ก ์ง์ํ์ง ์๋๋ค.\n this.many = costOf(blueprint, 10000)\n this.score = scoreOf(blueprint)\n this.capacity = capacityOf(this.cost)\n\n // ๊ฐ์๋ฅผ ๋ฐ์ผ๋ก ์๋ฆฐ๋ค. ํญ ์ด๋ฆํ๊ฐ ์ด ๊ฐ์ ๋ณด์ฌ ์ฃผ๋๋ฐ, ๊ฑฐ๊ธฐ์ ๋ค์ ์
ํ๋ฉด\n // ๊ฐ์ ํ์์ด ๋ ์๋ฆฌ์์ ๋ค๋ฅด๊ฒ ๋์ฌ ์ ์๋ค.\n this.dispatchEvent(\n new CustomEvent('verdict-changed', {\n detail: { instances: this.capacity?.instances, grade: this.score?.grade },\n bubbles: true,\n composed: true\n })\n )\n this.curve = costCurveSvg(blueprint)\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"figure-report.js","sourceRoot":"","sources":["../../client/modeller/figure-report.ts"],"names":[],"mappings":"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","sourcesContent":["import '@material/web/icon/icon.js'\n\nimport { css, html, LitElement, nothing, svg } from 'lit'\nimport { customElement, property, state } from 'lit/decorators.js'\nimport { unsafeSVG } from 'lit/directives/unsafe-svg.js'\n\nimport { i18next, localize } from '@operato/i18n'\nimport { ScrollbarStyles } from '@operato/styles'\nimport { blocksRelease, compile, costCurveSvg, costOf, scoreOf, sizingReport, validate } from '@hatiolab/figure-model'\nimport type { FigureCost, FigureScore, FigureSource } from '@hatiolab/figure-model'\n\nimport { capacityOf, MEASURED } from './scene-budget.js'\nimport { maturityOf } from './maturity.js'\nimport type { MaturityAxis } from './maturity.js'\nimport type { FigureCapacity } from './scene-budget.js'\n\n/**\n * ํ๋จ ํจ๋. ๋ชจ๋ธ๋ฌ ํ๋ฉด์ **๋ ๋ ์๋ค.**\n *\n * ์ ์ฅ์ ์ ํํด์ผ ์๋ ๊ฒ์ด ์๋๋ค. ๋ถํ์ ํ๋ ๋์ ๋๋ง๋ค ๋ฌด๊ฒ์ ์ ์๊ฐ ์์ง์ด๊ณ ,\n * ๊ทธ๊ฒ์ด ๋ณด์ฌ์ผ ์ ์์๊ฐ ๊ณ ์น ์ ์๋ค. ใ๋ฌด์ ๋๋ฌธ์ ์ ์๊ฐ ๋ฎ์๊ฐใ๋ฅผ ๋งํด ์ฃผ์ง\n * ์์ผ๋ฉด ์ ์๋ ์์๋ฆฌ์ผ ๋ฟ์ด๋ค.\n *\n * ## ์
์ ์ฌ๊ธฐ์ ํ์ง ์๋๋ค\n *\n * ๊ฒ์ฆยท์๊ฐยท์ ์๋ ์ ๋ถ `@hatiolab/figure-model` ์ด ํ๋ค. ํ๋ฉด์ **๋ถ๋ฅด๊ณ ๋ณด์ฌ ์ค\n * ๋ฟ**์ด๋ค. ํ๋๋ ๋ฑ๊ธ ๊ฒฝ๊ณ๋ฅผ ํ๋ฉด์ด ๋ค์ ์ ํ๋ฉด ์๋ฒ๊ฐ ๊ฑฐ์ ํ ๊ฒ์ ํ๋ฉด์ด\n * ํต๊ณผ์ํค๊ฒ ๋๋ค.\n */\n@customElement('figure-report')\nexport class FigureReport extends localize(i18next)(LitElement) {\n static styles = [\n ScrollbarStyles,\n css`\n :host {\n display: flex;\n flex-direction: column;\n overflow-y: auto;\n background-color: var(--md-sys-color-surface-container-lowest);\n border-left: 1px solid var(--md-sys-color-outline-variant);\n color: var(--md-sys-color-on-surface);\n font: var(--label-font, inherit);\n /*\n ์ด ํจ๋์ ๋ณธ๋ฌธ ํฌ๊ธฐ๋ฅผ ์ฌ๊ธฐ์ ํ ๋ฒ ์ ํ๋ค.\n\n ์ ์๋ ๊ท์น๋ง๋ค ๋ฐ๋ก ์ ์๋ค. ๊ทธ๋ฌ๋ฉด ๋น ๋จ๋ฆฐ ๊ท์น์ด ๋ณธ๋ฌธ ๊ธฐ๋ณธ ํฌ๊ธฐ(1rem)๋ฅผ\n ๋ฌผ๋ ค๋ฐ์ ๊ทธ ์ค๋ง ์ ๋ชฉ์ฒ๋ผ ์ปค์ง๋ค. ์ค๋ฅ๊ฐ ์๋๋ผ์ ํ๋ฉด์ ๋์ ๋ด์ผ ์๋ค.\n ์ด ํ์ผ์์๋ง ๋ ๋ฒ ๋ฌ๋ค.\n\n form ์์(input ยท select ยท button)๋ ๊ธ๊ผด์ ๋ฌผ๋ ค๋ฐ์ง ์์ผ๋ฏ๋ก ๊ฐ์ ์ ์ด์ผ ํ๋ค.\n ๊ทธ๊ฒ ๋ง๊ณ ๋ ์ฌ๊ธฐ ๊ฐ์ ๋ฐ๋ฅธ๋ค.\n */\n font-size: 0.76rem;\n }\n\n section {\n padding: var(--spacing-medium, 8px) var(--spacing-large, 12px);\n border-bottom: 1px solid var(--md-sys-color-outline-variant);\n }\n section > h3 {\n margin: 0 0 6px 0;\n font-size: var(--ui-t-micro, 11px);\n font-weight: 700;\n letter-spacing: 0.04em;\n text-transform: uppercase;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n\n /* โโ ๋ช ๊ฐ๊น์ง ํธํ๊ฐ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ\n ๋ก์ฐํด๋ฆฌ์ ๊ฐ์ ใ์ผ๋ง๋ ๋ง์ด ํธํ๊ฒ ๋์ ์ ์๋ใ๋ค. ๊ทธ ๋ต์ด ๋จธ๋ฆฌ์ ์จ๋ค.\n ๋ฑ๊ธ์ ํ์ ์์ฒด๊ฐ ํ๋ ์์ธ์ง๋ฅผ ๋งํ ๋ฟ์ด๋ผ ์์ ์์ badge ๋ก ๋๋ค. */\n div[verdict] {\n display: flex;\n align-items: baseline;\n gap: 6px;\n }\n span[capacity] {\n font-size: 2.1rem;\n font-weight: 800;\n line-height: 1;\n letter-spacing: -0.01em;\n color: var(--md-sys-color-primary);\n }\n span[unit] {\n font-size: 0.9rem;\n font-weight: 600;\n color: var(--md-sys-color-primary);\n }\n /*\n ๋ฑ๊ธ badge.\n\n ์ ์๋ \"C 0\" ๋ง ์์๋ค. ๊ธ์ ํ๋์ ์ซ์ ํ๋์ธ๋ฐ ์ด๋์๋ ๋ป์ด ์์ด์, ํฌ๊ฒ ๋ฌ\n ๊ฐ์ ์์ ๋นจ๊ฐ badge ๊ฐ ๋ถ์ ๊ฒ์ผ๋ก๋ง ์ฝํ๋ค. 0 ์ 100์ ๋ง์ ์ 0 ์ ์ผ๋ก ์ฝ๋ ๊ฒ์ด\n ์์ฐ์ค๋ฝ๋ค. ์ค์ ๋ป์ \"์ ์ธํ ํ๋์ ๋จ์ ์ฌ์ ๊ฐ 0\" ์ด๋ค.\n\n ๊ทธ๋์ ๋ฌด์์ ์ธก์ ํ๋์ง๋ฅผ badge ์์ ์ ๊ณ , ๋๊ธ์ ๋ฐ๋ก ์๋ ์ค์ ๋ ๋ณด์ด๊ฒ ๋๋ค.\n */\n span[grade] {\n display: flex;\n align-items: baseline;\n gap: 5px;\n margin-left: auto;\n padding: 3px 10px;\n font-size: 0.76rem;\n font-weight: 700;\n color: var(--md-sys-color-on-primary-container);\n background-color: var(--md-sys-color-primary-container);\n border-radius: 999em;\n }\n span[grade] small {\n font-size: 0.68rem;\n font-weight: 500;\n }\n /*\n C ๋ ํ๋๋ฅผ ์งํจ ๊ฒ์ด๋ค. ๋นจ๊ฐ์ ๋๊ธด ๊ฒ(D)์๋ง ์ด๋ค. ์งํจ ๊ฒ์ ๋นจ๊ฐ์ ์ฐ๋ฉด\n ๊ณ ์น ๊ฒ์ด ์๋๋ฐ๋ ๊ณ ์ณ์ผ ํ ๊ฒ์ฒ๋ผ ๋ณด์ธ๋ค.\n */\n span[grade][tight] {\n color: var(--md-sys-color-on-tertiary-container, #3d2f00);\n background-color: var(--md-sys-color-tertiary-container, #ffdf9a);\n }\n /*\n Pair the container with its on-container.\n\n This used to fill with --md-sys-color-error and write with\n --md-sys-color-on-error-container. Once the palette made containers\n neutral and moved the meaning into the text colour, those two became the\n same red and the badge went blank -- a filled pill with no readable text.\n */\n span[grade][over] {\n color: var(--md-sys-color-on-error-container);\n background-color: var(--md-sys-color-error-container);\n }\n\n /* ๋ฑ๊ธ ๋๊ธ. ์ ์ด ๋์ง ์๋๋ค โ ํ ๋ฒ ๋ณด๊ณ ๋ง๋ ๊ฐ์ด ์๋๋ผ ๋ณผ ๋๋ง๋ค ํ์ํ๋ค */\n p[scale] {\n display: flex;\n flex-wrap: wrap;\n gap: 2px 10px;\n margin: 6px 0 0 0;\n font-size: 0.7rem;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n p[scale] b {\n font-weight: 700;\n }\n p[scale] span[now] b {\n color: var(--md-sys-color-primary);\n }\n p[scale] span[now] {\n color: var(--md-sys-color-on-surface);\n }\n /* ์ด ํฐ ์ซ์๊ฐ ์ด๋ ์ถ์ธ์ง ๋จผ์ ๋งํ๋ค โ ์ฑ์๋์ ํ ์ถ์ด์ง ์ ๋ถ๊ฐ ์๋๋ค */\n p[lead] {\n margin: 0 0 4px 0;\n font-size: 0.74rem;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n\n /* ๊ทผ๊ฑฐ๋ฅผ ํจ๊ป ๋ธ๋ค โ ์ซ์๋ง ํฌ๊ฒ ๋ด๊ฑธ๋ฉด ์ฌ ๋ณธ ๊ฐ์ฒ๋ผ ์ฝํ๋ค */\n p[basis] {\n margin: 6px 0 0 0;\n font-size: 0.72rem;\n line-height: 1.55;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n p[basis] em {\n font-style: normal;\n color: var(--md-sys-color-tertiary);\n }\n span[score] {\n font-size: 0.8rem;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n\n /* ๋ฌด์ ๋๋ฌธ์ ์ด ๋ฑ๊ธ์ธ๊ฐ โ ํ๋์ ๊ฐ์ฅ ๊ฐ๊น์ด ํญ๋ชฉ */\n p[because] {\n margin: 8px 0 0 0;\n /* ๋ณธ๋ฌธ ํฌ๊ธฐ๋ฅผ ๋ฌผ๋ ค๋ฐ์ผ๋ฉด ์ด ์ค๋ง ์ ๋ชฉ์ฒ๋ผ ์ปค์ง๋ค โ ํ๋ฉด์ ๋์ ๋ณด๊ณ ์์๋ค */\n font-size: 0.78rem;\n line-height: 1.6;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n p[because] strong {\n color: var(--md-sys-color-on-surface);\n }\n\n /* โโ ์ฑ์๋ radar โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ\n ์ฌ์ฏ ์ถ์ ํ ๊ทธ๋ฆผ์ผ๋ก. ๋ชฉ๋ก๋ง ๋๋ฉด ใ์ด๋ ์ชฝ์ด ๋ชจ์๋๊ฐใ๊ฐ ์ ๋ณด์ธ๋ค.\n ๋ชป ์ฐ ์ถ์ ์ ์ ์ฐ์ง ์๊ณ ์ด๋ง ํ๋ฆฌ๊ฒ ๋จ๊ธด๋ค โ 0 ์ผ๋ก ์ฐ์ผ๋ฉด ใ๋์๋คใ๊ฐ ๋๋ค. */\n div[radar] {\n display: flex;\n justify-content: center;\n padding: 2px 0 6px 0;\n color: var(--md-sys-color-primary);\n }\n div[radar] svg {\n width: 100%;\n max-width: 240px;\n height: auto;\n }\n div[radar] polygon[web] {\n fill: none;\n stroke: var(--md-sys-color-outline-variant);\n stroke-width: 0.6;\n }\n div[radar] line[spoke] {\n stroke: var(--md-sys-color-outline-variant);\n stroke-width: 0.6;\n }\n div[radar] polygon[shape] {\n fill: color-mix(in srgb, var(--md-sys-color-primary) 22%, transparent);\n stroke: var(--md-sys-color-primary);\n stroke-width: 1.4;\n stroke-linejoin: round;\n }\n div[radar] circle[dot] {\n fill: var(--md-sys-color-primary);\n }\n div[radar] text {\n font-size: 5.2px;\n fill: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n\n /* ๊ทธ๋ฆผ์ ์๋ฆฌ๋ฅผ ์ฃผ์ง ์์ ์ถ์ ๊ธ๋ก ๋ฐํ๋ค */\n p[unmeasured] {\n margin: 0 0 8px 0;\n font-size: 0.7rem;\n line-height: 1.5;\n color: var(--md-sys-color-tertiary);\n }\n\n /* โโ ์ฑ์๋ ์ถ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ\n ํ ์ซ์๋ก ํฉ์น์ง ์๋๋ค. ํฉ์น๋ฉด ใ๋ฌด์์ ๊ณ ์ณ์ผ ํ๋ใ๊ฐ ์ฌ๋ผ์ง๋ค. */\n ul[axes] {\n margin: 0;\n padding: 0;\n list-style: none;\n display: flex;\n flex-direction: column;\n gap: 7px;\n }\n ul[axes] li {\n display: grid;\n grid-template-columns: 1fr auto;\n gap: 2px 8px;\n font-size: 0.75rem;\n }\n ul[axes] li[blocked] {\n opacity: 0.7;\n }\n ul[axes] em {\n grid-column: 1 / -1;\n font-style: normal;\n font-size: 0.68rem;\n line-height: 1.5;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n /* ๋ชป ์ฐ ์ถ์ 0 ์ผ๋ก ๋์ง ์๋๋ค โ 0 ์ ใ๋์๋คใ๋ ๋ป์ด ๋์ด ๋ฒ๋ฆฐ๋ค */\n ul[axes] li[blocked] em {\n color: var(--md-sys-color-tertiary);\n }\n span[reading] {\n font-family: var(--mono-font, monospace);\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n\n /* โโ ์์ฐ ๋ง๋ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ */\n ul[budgets] {\n margin: 0;\n padding: 0;\n list-style: none;\n display: flex;\n flex-direction: column;\n gap: 6px;\n }\n ul[budgets] li {\n display: grid;\n grid-template-columns: 1fr auto;\n gap: 2px 8px;\n font-size: 0.75rem;\n }\n div[bar] {\n grid-column: 1 / -1;\n height: 4px;\n background-color: var(--md-sys-color-surface-container-highest);\n border-radius: 2px;\n overflow: hidden;\n }\n div[bar] > i {\n display: block;\n height: 100%;\n background-color: var(--md-sys-color-primary);\n }\n div[bar] > i[tight] {\n background-color: var(--md-sys-color-error);\n }\n\n /* โโ ๋ฌด๊ฒ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ */\n dl[metrics] {\n margin: 0;\n display: grid;\n grid-template-columns: 1fr auto;\n gap: 4px 8px;\n font-size: 0.78rem;\n }\n dl[metrics] dt {\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n dl[metrics] dd {\n margin: 0;\n text-align: right;\n font-family: var(--mono-font, monospace);\n }\n\n /* โโ ์ถ์ด โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ\n ๊ทธ๋ฆผ์ ์์ฐ ํฌ๊ธฐ๊ฐ 680px ๋ค. 300px ์นธ์ ๋ฃ์ผ๋ฉด ๊ธ์๊ฐ 4px ์ด ๋์ด ์๋ฌด๊ฒ๋\n ์ฝ์ ์ ์๋ค โ ์ฌ์ด๋๋ฐ์๋ ์ซ์๋ฅผ ๋๊ณ , ๊ทธ๋ฆผ์ ์ ํํด์ ํฌ๊ฒ ๋ณธ๋ค. */\n button[expand] {\n margin-top: 6px;\n padding: 4px 10px;\n font: var(--label-font, inherit);\n font-size: 0.74rem;\n color: var(--md-sys-color-on-surface);\n background: none;\n border: 1px solid var(--md-sys-color-outline-variant);\n border-radius: 6px;\n cursor: pointer;\n }\n button[expand]:hover {\n background-color: var(--md-sys-color-surface-container);\n }\n\n div[sheet] {\n position: fixed;\n inset: 0;\n z-index: 10;\n display: flex;\n align-items: center;\n justify-content: center;\n padding: var(--spacing-large, 12px);\n background-color: rgba(0, 0, 0, 0.32);\n }\n div[sheet] > figure {\n max-width: 100%;\n max-height: 100%;\n margin: 0;\n padding: var(--spacing-large, 12px);\n overflow: auto;\n color: var(--md-sys-color-primary);\n background-color: var(--md-sys-color-surface-container-lowest);\n /* ๋ด๋ ๋ฉด์ด ํ์
์ด๋ฉด ์์ชฝ ๋ชจ์๋ฆฌ๋ ์์ฝ์ด๋ค โ ์ํธ ์์ฒด๋ ํ์ด์ง ๊ฐ์ ์ด๋ค */\n border-radius: 6px;\n box-shadow: 0 8px 32px rgba(0, 0, 0, 0.28);\n }\n div[sheet] svg {\n display: block;\n /* ์์ฐ ํฌ๊ธฐ๋ณด๋ค ์๊ฒ ์ค์ด์ง ์๋๋ค โ ์ข์ผ๋ฉด ๋๊ฒจ ๋ณด๊ฒ ๋๋ค */\n min-width: 680px;\n }\n div[sheet] figcaption {\n display: flex;\n align-items: center;\n justify-content: flex-end;\n }\n div[sheet] button[close] {\n padding: 5px 14px;\n font: var(--label-font, inherit);\n color: var(--md-sys-color-on-surface);\n background: none;\n border: 1px solid var(--md-sys-color-outline-variant);\n border-radius: 999em;\n cursor: pointer;\n }\n\n /* โโ ์๋ฆผ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ */\n ul[findings] {\n margin: 0;\n padding: 0;\n list-style: none;\n display: flex;\n flex-direction: column;\n gap: 6px;\n }\n ul[findings] li {\n display: flex;\n gap: 6px;\n line-height: 1.5;\n }\n ul[findings] md-icon {\n --md-icon-size: 16px;\n flex: none;\n color: var(--md-sys-color-error);\n }\n ul[findings] li[violation] md-icon {\n color: var(--md-sys-color-tertiary);\n }\n /* ์ด๊ธด ์๋ฆฌ. ๋ฌธ๊ตฌ์ ๋ถ์ด ํ๋ฅด๋ฉด ๋ฌธ์ฅ์ ์ผ๋ถ๋ก ์ฝํ๋ค โ badge ๋ก ๋ณด์ด๊ฒ ๋๋ค */\n code[at] {\n padding: 1px 5px;\n font-family: var(--mono-font, monospace);\n font-size: 0.68rem;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n background-color: var(--md-sys-color-surface-container);\n border-radius: 4px;\n white-space: nowrap;\n }\n\n /*\n ๋ฐ๊ฒฌ์ด ์์ ๋์ ๋ฌธ๊ตฌ.\n\n ํฌ๊ธฐ๋ฅผ ์ ์ ์ด ๋์๋๋ ๋ณธ๋ฌธ ๊ธฐ๋ณธ ํฌ๊ธฐ๋ฅผ ๋ฌผ๋ ค๋ฐ์ ์ด ์ค๋ง ์ ๋ชฉ์ฒ๋ผ ์ปค์ก๋ค. ์ด\n ํจ๋์ ๊ธ์๋ ์ ๋ถ 0.7rem ๋์ธ๋ฐ ์ฌ๊ธฐ๋ง 1rem ์ด๋ผ ์๋์ชฝ์ด ๋ฌด๋์ ธ ๋ณด์๋ค.\n\n ์ฐพ์ ๊ฒ์ด ์์ ๋์ ๋ชฉ๋ก(ul[findings] li)๊ณผ ๊ฐ์ ํฌ๊ธฐ๋ก ๋ง์ถ๋ค. ์์ ๋์ ์์ ๋\n ์ ์ ์๊น์๊ฐ ๋ฌ๋ผ์ง ์ด์ ๊ฐ ์๋ค.\n\n ์ด ํ์ผ์์ ๊ฐ์ ์ค์๋ฅผ ๋ ๋ฒ์งธ๋ก ํ๋ค. p[because] ์๋ ๊ฐ์ ์ฃผ์์ด ์๋ค.\n */\n p[quiet] {\n margin: 0;\n font-size: 0.76rem;\n line-height: 1.6;\n color: var(--md-sys-color-on-surface-variant, var(--md-sys-color-on-surface));\n }\n `\n ]\n\n /** ์ ์ ์ค์ธ ์๋ณธ ๋ฐ์ดํฐ. ๋ฐ๋๋ฉด ๋ค์ ์ธก์ ํ๋ค. */\n @property({ type: Object }) source?: FigureSource\n\n @state() private cost?: FigureCost\n @state() private score?: FigureScore\n @state() private curve = ''\n /** 1๋ง ๊ฐ๋ฅผ ๋์์ ๋. ์ ์์๊ฐ ์ค์ ๋ก ๊ถ๊ธํ ์ซ์๋ค. */\n @state() private many?: FigureCost\n /** ๋ช ๊ฐ๊น์ง ๋์ ์ ์๋. ์ด ํจ๋์ ๋จธ๋ฆฌ๋ค. */\n @state() private capacity?: FigureCapacity\n /** ์ถ์ด ๊ทธ๋ฆผ์ ์ ํฌ๊ธฐ๋ก ํผ์ณค๋. */\n @state() private expanded = false\n @state() private errors: { code: string; message: string; at?: string }[] = []\n /**\n * ํ์์ด ๊ถํ์ง ์๋ ๊ฒ โ **๊ทธ์ค ๋์ ๋ฐํ์ ๋ง๋๋ค.**\n *\n * ๋ฑ๊ธ์ ํ์์์ ๋ฐ๋๋ค(`blocksRelease`). ํ๋ฉด์ด ์ ๋ชฉ๋ก์ ๋ค๋ฉด ํ์์ ์ฝ๋๊ฐ ํ๋ ๋ ๋\n * ์กฐ์ฉํ ใ์๋ฆผใ์ผ๋ก ๊ทธ๋ ค์ง๊ณ , ์ ์์๋ ๋ฐํ์ด ๋งํ ๊ฒ์ **๋๋ฌ ๋ณด๊ณ ๋์์ผ** ์๋ค.\n *\n * `actual` ์ ์ผ๋ง๋ ๋์ณค๋๋ค. ใ์์๋ฅผ ๋ฒ์ด๋๋คใ๋ง์ผ๋ก๋ 2mm ์ธ์ง 250mm ์ธ์ง ๋ชจ๋ฅด๊ณ ,\n * ๊ทธ ๋์ ๊ณ ์น๋ ํ์ด ๋ค๋ฅด๋ค.\n */\n @state() private violations: { code: string; message: string; blocking: boolean; actual?: number }[] = []\n /**\n * ํฌ๊ธฐ๋ฅผ ๋ฐ๊ฟ ๋ดค์ ๋ ๊ฐ๋ผ์ง๋๊ฐ โ **๋ฐํ์ ๋ง๋ ๊ฒ**์ด๋ค.\n *\n * ์ด๋ ฅ ํญ์ด ๊ฐ์ ํ์ ์ ์๋ฒ์์ ๋ฐ์ ๋ฐํ ๋ฌธ์ ์ ๊ทธ์ง๋ง, ๊ทธ๊ฒ์ **์ ์ฅ๋ ์ ๋ณธ**์ ๋ํ\n * ๊ฒ์ด๋ผ ์ ์ฅํ๊ธฐ ์ ์๋ ๋ตํ์ง ๋ชปํ๋ค. ์ฌ๊ธฐ์๋ ์ ์ ์ค์ธ ์ ๋ณธ์ ๊ทธ๋๋ก ์ฌ๋ฏ๋ก, ๋ถํ์\n * ์ฎ๊ธฐ๋ ๊ทธ ์๋ฆฌ์์ ๊ฐ๋ผ์ง์ด ์๊ฒผ๋์ง ์ฌ๋ผ์ก๋์ง ๋ณด์ธ๋ค โ ์ ์ฅํ๊ณ ํญ์ ์ฎ๊ฒจ ํ์ธํ๊ฒ\n * ๋๋ฉด ๊ณ ์น ๋๊ฐ ์ด๋ฏธ ์ง๋ ์๋ค.\n */\n @state() private sizing: { code: string; message: string; at?: string; blocking: boolean }[] = []\n /**\n * ์์ง ๋ถํ์ด ํ๋๋ ์๋ โ **์ ์ ์ ์ด์ง ํ์์ ์ด๊ธด ๊ฒ์ด ์๋๋ค.**\n *\n * ํ์์ ๋ถํ 0๊ฐ๋ฅผ ์ค๋ฅ๋ก ๋ณธ๋ค(`missing-parts`). ๋ฐํ ๊ด์ ์์๋ ๋ง๋ค. ๊ทธ๋ฐ๋ฐ ์๋ก ๋ง๋ค๊ธฐ๋ฅผ\n * ๋๋ฅธ ์งํ๊ฐ ๋ฐ๋ก ๊ทธ ์ํ์ด๋ฏ๋ก, ๊ทธ๊ฒ์ ๊ทธ๋๋ก ์ค๋ฅ๋ก ๊ทธ๋ฆฌ๋ฉด **์๋ฌด๊ฒ๋ ํ์ง ์์๋๋ฐ ๋ถ์\n * ํ๋ฉด**์ ๋ณด๊ฒ ๋๋ค. ๊ทธ๋์ ์ด ์๋ฆฌ์์ ๋์ ๊ฐ๋ฅธ๋ค.\n */\n @state() private bare = false\n\n willUpdate(changed: Map<string, unknown>) {\n if (changed.has('source')) {\n this.measure()\n }\n }\n\n render() {\n /*\n ๋ถํ์ด ์์ผ๋ฉด ์ด ์๋ฆฌ๋ **ํ์ ์ด ์๋๋ผ ์๋ด**๋ค. ์ด๋ฏธ ์๋ ใ๋ถํ์ ์ถ๊ฐํ๋ฉด ๋์ต๋๋คใ๊ฐ\n ์ ํํ ๊ทธ ๋ง์ด๋ฏ๋ก ๊ทธ๊ฒ์ ์ด๋ค โ ๊ฐ์ ์ํ์ ๋ฌธ์ฅ์ ๋ ๋์ง ์๋๋ค.\n\n ์๋ ์
๋ค(๋จธ๋ฆฌยท์ถยทํ๋ยท์ถ์ด)์ ๋ถํ์ด ์์ด์ผ ๋ป์ด ์๊ณ , ์ฌ์ง ์์ ๊ฐ์ ๋ค๊ณ ๊ทธ๋ฆฌ๋ฉด 0 ์ผ๋ก\n ๋ณด์ธ๋ค. 0 ์ ใ๋์๋คใ๋ก ์ฝํ๋ฏ๋ก ๊ทธ ์๋ฆฌ์ ๋์ง ์๋๋ค.\n */\n if (!this.source || this.bare) {\n return html`\n <section>\n <p quiet>${i18next.t('figure.text.report-appears-when-you-add-a-part')}</p>\n </section>\n `\n }\n\n // ํ์์ ์ด๊ธด ์ํ์์๋ ์
์ด ๋ป์ ๊ฐ์ง ๋ชปํ๋ค โ ๋ฌด์์ด ์๋ชป๋๋์ง๋ง ๋ณด์ฌ ์ค๋ค.\n if (this.errors.length > 0) {\n return html`${this.renderFindings()}`\n }\n\n return html`\n ${this.renderVerdict()} ${this.renderAxes()} ${this.renderBudgets()} ${this.renderMetrics()} ${this.renderCurve()}\n ${this.renderFindings()} ${this.renderSheet()}\n `\n }\n\n /**\n * ๋จธ๋ฆฌ โ ๋ช ๊ฐ๊น์ง ํธํ๊ฐ.\n *\n * ๋ก์ฐํด๋ฆฌ์ ๊ฐ์ ใ์ผ๋ง๋ ๋ง์ด ํธํ๊ฒ ๋์ ์ ์๋ใ์ ์๋ค. ๋ฑ๊ธ B ๋ ๊ทธ ๋ฌผ์์\n * ์ง์ ๋ตํ์ง ์๋๋ค โ ํ์์ด ์ ์ธ๋ ํ๋ ์์ธ์ง๋ฅผ ๋งํ ๋ฟ์ด๋ค. ๊ทธ๋์ ๊ฐ์๋ฅผ\n * ๋จธ๋ฆฌ์ ์ฌ๋ฆฌ๊ณ ๋ฑ๊ธ์ ์์ badge ๋ก ๋ด๋ฆฐ๋ค.\n *\n * ๊ทผ๊ฑฐ๋ฅผ ํจ๊ป ๋ธ๋ค. ๋ฌถ์์ผ๋ก ๊ฐ๋ฆฌ๋ ๊ฐ์์ ๋ถ๋ชจ๋ **์ค์ธก**์ด๊ณ (2026-09-18, Apple M5), ์ฐ\n * ๊ธฐ๊ณ์ ๋ ์ง๋ฅผ ํจ๊ป ์ ๋๋ค โ ์ ์ง ์์ผ๋ฉด ์ด๋์๋ ์ฐธ์ธ ์๋ก ์ฝํ๋ค. ์ผ๊ฐํ ์ชฝ์ ์์ง ์ค๊ณ\n * ๋ฌธ์์ ๋ชฉํ์น๋ผ ๊ทธ๋ ๋ค๊ณ ์ ๋๋ค.\n */\n private renderVerdict() {\n const score = this.score\n const capacity = this.capacity\n if (!score || !capacity) return nothing\n\n return html`\n <section>\n <h3>${i18next.t('figure.label.maturity')}</h3>\n <p lead>${i18next.t('figure.label.axis-scale')} โ ${i18next.t('figure.text.how-many-fit')}</p>\n <div verdict>\n <span capacity>${capacity.instances.toLocaleString()}</span>\n <span unit>${i18next.t('figure.text.instances-unit')}</span>\n <span\n grade\n ?tight=${score.grade === 'C'}\n ?over=${score.grade === 'D'}\n title=${i18next.t('figure.text.grade-explained')}\n >\n ${score.grade}\n <small>${i18next.t('figure.text.headroom-percent', { percent: Math.round(score.score) })}</small>\n </span>\n </div>\n <p because>\n ${i18next.t('figure.text.grade-decided-by')}\n <strong>${i18next.t('figure.label.budget-' + score.tightest.key)}</strong>\n โ ${score.tightest.used} / ${score.tightest.limit}\n (${Math.round((score.tightest.used / score.tightest.limit) * 100)}%)\n </p>\n ${this.renderGradeScale(score.grade)}\n <p basis>\n ${i18next.t('figure.text.bound-by-' + capacity.bound, {\n per: capacity.per.toLocaleString(),\n budget: capacity.budget.toLocaleString()\n })}\n <em>\n ${capacity.bound === 'groups'\n ? i18next.t('figure.text.budget-measured-on', { gpu: MEASURED.gpu, on: MEASURED.on })\n : i18next.t('figure.text.budget-not-measured-yet')}\n </em>\n </p>\n </section>\n `\n }\n\n /**\n * ๋ฑ๊ธ ๋๊ธ.\n *\n * AยทBยทCยทD ๊ฐ ๋ฌด์์ ๋ปํ๋์ง ํ๋ฉด ์ด๋์๋ ์์๋ค. badge ๋ง ๋ณด๊ณ ๋ ์ข์์ง ๋์์ง๋,\n * ๋ฌด์์ ๊ณ ์ณ์ผ ์ค๋ฅด๋์ง๋ ์ ์ ์๋ค. ๋๊ธ์ ๋ ๊ณ์ ๋๊ณ ์ง๊ธ ์ด๋์ ์๋์ง๋ฅผ\n * ํ์ํ๋ค.\n *\n * ์ ์ด ๋์ง ์๋๋ค. ํ ๋ฒ ๋ฐฐ์ฐ๊ณ ๋ง๋ ๊ฐ์ด ์๋๋ผ ๋ณผ ๋๋ง๋ค ๋์กฐํ๋ ๊ฐ์ด๋ค.\n */\n private renderGradeScale(now: string) {\n const bounds: [string, string][] = [\n ['A', 'โค 50%'],\n ['B', 'โค 75%'],\n ['C', 'โค 100%'],\n ['D', '> 100%']\n ]\n\n return html`\n <p scale>\n <span>${i18next.t('figure.text.grade-scale-lead')}</span>\n ${bounds.map(\n ([grade, bound]) => html`<span ?now=${grade === now}><b>${grade}</b> ${bound}</span>`\n )}\n </p>\n `\n }\n\n /**\n * ์ฑ์๋ โ ์ฌ๋ฌ ์ถ์ผ๋ก ๋ณธ๋ค.\n *\n * ใ๋ช ๊ฐ๊น์ง ํธํ๊ฐใ ํ๋๋ก๋ ์ข์ ํ์๊ณผ ๋์ ํ์์ด ๊ตฌ๋ถ๋์ง ์๋๋ค. ๋ถํ ํ๋์ง๋ฆฌ\n * ์์๋ ๊ทธ ์ถ์์๋ ๋ง์ ์ด๋ค.\n *\n * **๋ชป ์ฌ๋ ์ถ์ 0 ์ผ๋ก ๋์ง ์๋๋ค.** 0 ์ ใ๋์๋คใ๋ ๋ป์ด ๋๋๋ฐ, ์ฌ์ค์ ์์ง\n * ์ธก์ ํ ๋ฐฉ๋ฒ์ด ์๋ ๊ฒ์ด๋ค. ์ธก์ ํ์ง ๋ชปํ๋ค๊ณ ์๋ฆฌ๊ณ ์ด์ ๋ฅผ ๋ถ์ธ๋ค. ์ง์ด๋ธ ์ ์๋ณด๋ค ๊ทธ๊ฒ์ด\n * ์ด ๋ฆฌํฌํธ๋ฅผ ๋ฏฟ์ ๋งํ๊ฒ ๋ง๋ ๋ค.\n */\n private renderAxes() {\n if (!this.cost || !this.score || !this.source) return nothing\n\n /*\n ๊ท๋ชจ๋ ๋ชฉ๋ก์์ ๋บ๋ค โ ๋จธ๋ฆฌ๋ก ์ฌ๋ผ๊ฐ๋ค. ๊ฐ์ ์ซ์๋ฅผ ๋ ๋ฒ ๋ด๋ฉด ์ฝ๋ ์ฌ๋์ด\n ๋์ด ๋ค๋ฅธ ๊ฒ์ธ ์ค ์๋ค.\n */\n const axes = maturityOf(this.source, this.cost, this.score).filter(axis => axis.key !== 'scale')\n\n // radar ์๋ ์ฌ์ฏ์ ๋ค ๊ทธ๋ฆฐ๋ค. ๊ท๋ชจ๊ฐ ์ด๋์ฏค์ธ์ง ํจ๊ป ๋ณด์ฌ์ผ ๋ป์ด ์๋ค\n const all = maturityOf(this.source, this.cost, this.score)\n\n return html`\n <section>\n <h3>${i18next.t('figure.label.by-axis')}</h3>\n <div radar>${this.renderRadar(all.filter(axis => axis.ratio !== undefined))}</div>\n ${this.renderUnmeasured(all.filter(axis => axis.ratio === undefined))}\n <ul axes>\n ${axes.map(axis => this.renderAxis(axis))}\n </ul>\n </section>\n `\n }\n\n /**\n * ์ฑ์๋ radar. **์ธก์ ํ ์ถ๋ง ๊ทธ๋ฆฐ๋ค.**\n *\n * ์ธก์ ํ์ง ๋ชปํ๋ ์ถ๋ spoke ๋ฅผ ๊ทธ๋ ค ๋๊ณ ๋ํ๋ง ๊ฑด๋๋ฐ๋ ๋๊ฐ ์์๋ค. ๊ทธ๋ฌ๋ฉด ๊ทธ ๋ฐฉํฅ์ ๊ฐ๋ก์ง๋ฅด๋\n * ์ง์ ์ด ์๊ฒจ์ ๋ํ์ด ๊ทธ์ชฝ์ผ๋ก ์ํน ๋ค์ด๊ฐ ๊ฒ์ฒ๋ผ ๋ณด์ธ๋ค. 0 ์ผ๋ก ์ฐ์ง ์์ผ๋ ค๊ณ ํ\n * ์ผ์ธ๋ฐ ๊ฒฐ๊ณผ๋ 0 ์ผ๋ก ์ฐ์ ๊ฒ๊ณผ ๋๊ฐ์ด ์ฝํ๋ค. ์ ์ ์ด๊ณผ ๋ฌผ์ํ๋ก๋ ๊ทธ ์ธ์์ด\n * ์ง์์ง์ง ์์๋ค.\n *\n * ๊ทธ๋์ ์์ ๋นผ๊ณ , ๋ชป ์ฌ๋ ์ถ์ ๊ทธ๋ฆผ ์๋์ ๊ธ๋ก ์ ๋๋ค. ์ด ์ ์๋ ๊ฒ์ ๊ทธ๋ฆผ์\n * ์๋ฆฌ๋ฅผ ์ฃผ์ง ์๋ ํธ์ด ์ ์งํ๋ค.\n */\n private renderRadar(axes: MaturityAxis[]) {\n // ๊ทธ๋ฆผ ์์์๋ **์งง์ ์ด๋ฆ**์ ์ด๋ค. ๊ธด ์ด๋ฆ์ ๊ทธ๋๋ก ์ฐ๋ฉด ์ผ์ชฝ์ด ์๋ฆฐ๋ค โ\n // ํ๋ฉด์ ๋์ ๋ณด๊ณ ์์๋ค.\n const cx = 60\n const cy = 46\n const r = 28\n\n const at = (index: number, ratio: number) => {\n const angle = -Math.PI / 2 + (index * 2 * Math.PI) / axes.length\n return [cx + r * ratio * Math.cos(angle), cy + r * ratio * Math.sin(angle)]\n }\n\n const points = axes\n .map((axis, index) => at(index, Math.max(0.04, Math.min(1, axis.ratio ?? 0))).map(n => n.toFixed(1)).join(','))\n .join(' ')\n\n return svg`\n <svg viewBox=\"0 0 120 96\" aria-hidden=\"true\">\n ${[0.33, 0.66, 1].map(\n ring => svg`<polygon web points=${axes.map((_, i) => at(i, ring).map(n => n.toFixed(1)).join(',')).join(' ')}></polygon>`\n )}\n ${axes.map((_, index) => {\n const [x, y] = at(index, 1)\n return svg`<line spoke x1=${cx} y1=${cy} x2=${x.toFixed(1)} y2=${y.toFixed(1)}></line>`\n })}\n <polygon shape points=${points}></polygon>\n ${axes.map((axis, index) => {\n const [x, y] = at(index, Math.max(0.04, Math.min(1, axis.ratio ?? 0)))\n return svg`<circle dot cx=${x.toFixed(1)} cy=${y.toFixed(1)} r=\"1.4\"></circle>`\n })}\n ${axes.map((axis, index) => {\n const [x, y] = at(index, 1.28)\n const anchor = x < cx - 3 ? 'end' : x > cx + 3 ? 'start' : 'middle'\n return svg`\n <text x=${x.toFixed(1)} y=${(y + 1.8).toFixed(1)} text-anchor=${anchor}>\n ${i18next.t('figure.label.axis-' + axis.key + '-short')}\n </text>\n `\n })}\n </svg>\n `\n }\n\n /**\n * ๊ทธ๋ฆผ์ ์๋ ์ถ์ ๊ธ๋ก ๋ฐํ๋ค.\n *\n * ๋นผ๊ธฐ๋ง ํ๋ฉด ์ถ์ด ์ฌ์ฏ์ธ์ง ๋ค์ฏ์ธ์ง ์ ์ ์๊ณ , ์๋ ๊ฒ์ ์๋ค๊ณ ๋งํ์ง ์์ ์
์ด\n * ๋๋ค. ๋ฌด์์ ์์ง ๋ชป ์ฌ๋์ง ํ ์ค๋ก ์ ๋๋ค. ์ ๋ชป ์ฌ๋์ง๋ ์๋ ๋ชฉ๋ก์ ๊ทธ ํญ๋ชฉ์\n * ๊ทธ๋๋ก ์๋ค.\n */\n private renderUnmeasured(axes: MaturityAxis[]) {\n if (axes.length === 0) return nothing\n\n return html`\n <p unmeasured>\n ${i18next.t('figure.text.axes-not-measurable-yet', {\n axes: axes.map(axis => i18next.t('figure.label.axis-' + axis.key)).join(' ยท ')\n })}\n </p>\n `\n }\n\n private renderAxis(axis: MaturityAxis) {\n const name = i18next.t('figure.label.axis-' + axis.key)\n\n if (axis.blocked) {\n return html`\n <li blocked>\n <span>${name}</span>\n <span reading>${i18next.t('figure.text.not-measurable-yet')}</span>\n <em>${i18next.t(axis.blocked)}</em>\n </li>\n `\n }\n\n const ratio = Math.max(0, Math.min(1, axis.ratio ?? 0))\n return html`\n <li>\n <span>${name}</span>\n <span reading>${axis.readingKey ? i18next.t(axis.readingKey) : (axis.reading ?? '')}</span>\n <div bar><i style=\"width:${Math.round(ratio * 100)}%\"></i></div>\n ${axis.because ? html`<em>${i18next.t(axis.because)}</em>` : ''}\n </li>\n `\n }\n\n /**\n * ์์ฐ ๋ง๋.\n *\n * ์ซ์๋ง ๋์ด๋์ผ๋ฉด ์ด๋ ๊ฒ์ด ๊ฝ ์ฐผ๋์ง ๋์ ์ ๋ค์ด์จ๋ค. ํ๋์ ๊ฐ์ฅ ๊ฐ๊น์ด ํ๋๋ฅผ ์์ผ๋ก\n * ๊ตฌ๋ถํ๋ค. ๊ทธ๊ฒ์ด ์ ์๋ฅผ ์ ํ ํญ๋ชฉ์ด๋ค.\n *\n * ## `use.label` ์ ์ฐ์ง ์๋ ์ด์ \n *\n * `FigureBudgetUse` ์ `label` ๊ณผ `why` ๊ฐ ์๊ณ ใ์ ์์์๊ฒ ๊ทธ๋๋ก ๋ณด์ฌ ์ค๋คใ๊ณ \n * ์ ํ ์๋ค. ๊ทธ๋ฐ๋ฐ ๊ทธ ๋ฌธ๊ตฌ๊ฐ **ํ๊ตญ์ด๋ก ๊ตฌ์์ ธ** ์๋ค. ์ด ์ ํ์ 5์ธ์ด๋ฅผ ์ฐ๋ฏ๋ก\n * ๊ทธ๊ฒ์ ๊ทธ๋๋ก ์ค์ผ๋ฉด ๋ค๋ฅธ ์ธ์ด ์ฌ์ฉ์์๊ฒ ํ๊ตญ์ด๊ฐ ๋์จ๋ค.\n *\n * `budgets` ๋ **๋ฐฐ์ด**์ด๋ค. `Object.entries` ๋ก ๋๋ฉด ํค๊ฐ ์ธ๋ฑ์ค(0ยท1ยท2โฆ)๊ฐ ๋์ด\n * `figure.label.budget-0` ๊ฐ์ ์๋ ํค๋ฅผ ์ฐพ๋๋ค โ ํ๋ฉด์ ๋์ ๋ณด๊ณ ์์ผ ๋๋ฌ๋ฌ๋ค.\n * ๋ฐฐ์ด์ ๊ทธ๋๋ก ๋๊ณ `use.key` ๋ฅผ ์ด๋ค.\n *\n * ๊ทธ๋์ **์์ ๋ `key`** ๋ก ์ด ํ๋ฉด์ i18n ์ ์ฐพ๋๋ค. `key` ๋ ์ด๊ฑฐํ์ด๋ผ ํ์์\n * ์ผ๋ถ์ด๊ณ , ๋ฌธ๊ตฌ๋ ํ๋ฉด์ ๋ชซ์ด๋ค. figure-model ์ด ๋ฌธ๊ตฌ๋ฅผ ์ธ์ด ์ค๋ฆฝ์ผ๋ก ๋ฐ๊พธ๋ฉด\n * ๊ทธ๋ `label` ์ ์ธ ์ ์๋ค.\n */\n private renderBudgets() {\n const score = this.score\n if (!score) return nothing\n\n return html`\n <section>\n <h3>${i18next.t('figure.label.budgets')}</h3>\n <ul budgets>\n ${score.budgets.map(use => {\n const ratio = Math.min(1, use.ratio)\n const tight = use.key === score.tightest.key\n return html`\n <li>\n <span>${i18next.t('figure.label.budget-' + use.key)}</span>\n <span>${use.used} / ${use.limit}</span>\n <div bar><i ?tight=${tight} style=\"width:${Math.round(ratio * 100)}%\"></i></div>\n </li>\n `\n })}\n </ul>\n </section>\n `\n }\n\n private renderMetrics() {\n const cost = this.cost\n if (!cost) return nothing\n\n return html`\n <section>\n <h3>${i18next.t('figure.label.weight')}</h3>\n <dl metrics>\n <dt>${i18next.t('figure.label.triangles')}</dt>\n <dd>${cost.triangles.toLocaleString()}</dd>\n\n <dt>${i18next.t('figure.label.triangles-at-100')}</dt>\n <dd>${cost.at.triangles.toLocaleString()}</dd>\n\n <dt>${i18next.t('figure.label.draw-calls-at-100')}</dt>\n <dd>${cost.at.drawCalls.toLocaleString()}</dd>\n\n <dt>${i18next.t('figure.label.distinct-shapes')}</dt>\n <dd>${cost.distinctShapes}</dd>\n\n <dt>${i18next.t('figure.label.distinct-materials')}</dt>\n <dd>${cost.distinctMaterials}</dd>\n </dl>\n </section>\n `\n }\n\n /**\n * ์ฌํ์ฉ ์ถ์ด โ ใ๋ง์ด ๋์ผ๋ฉด ์ด๋ป๊ฒ ๋๋ใ์ ๋ตํ๋ค.\n *\n * ## ๊ทธ๋ฆผ์ ์ฌ์ด๋๋ฐ์ ๋ฐ์ด ๋ฃ์ง ์๋๋ค\n *\n * `costCurveSvg` ์ ์์ฐ ํฌ๊ธฐ๋ 680x380 ์ด๊ณ ๊ธ์๊ฐ 11px ๋ค. 300px ์นธ์์\n * width:100% ๋ก ์ค์ด๋ฉด ๊ธ์๊ฐ 4px ์ด ๋์ด **์๋ฌด๊ฒ๋ ์ฝ์ ์ ์๋ค** โ ํ๋ฉด์ ๋์\n * ๋ณด๊ณ ์์ผ ๋๋ฌ๋ฌ๋ค. ์ฝ์ ์ ์๋ ๊ทธ๋ฆผ์ ์๋ ๊ฒ๊ณผ ๊ฐ์ผ๋ฏ๋ก, ์ฌ์ด๋๋ฐ์๋ ์ ์์๊ฐ\n * ์ค์ ๋ก ๊ถ๊ธํ ์ซ์(1๋ง ๊ฐ์ผ ๋)๋ฅผ ๋๊ณ ๊ทธ๋ฆผ์ ์ ํํด์ ์ ํฌ๊ธฐ๋ก ๋ณธ๋ค.\n */\n private renderCurve() {\n const many = this.many\n if (!many && !this.curve) return nothing\n\n return html`\n <section>\n <h3>${i18next.t('figure.label.reuse-trend')}</h3>\n ${many\n ? html`\n <dl metrics>\n <dt>${i18next.t('figure.label.triangles-at-10k')}</dt>\n <dd>${many.at.triangles.toLocaleString()}</dd>\n\n <dt>${i18next.t('figure.label.draw-calls-at-10k')}</dt>\n <dd>${many.at.drawCalls.toLocaleString()}</dd>\n </dl>\n `\n : nothing}\n ${this.curve\n ? html`\n <button expand @click=${() => (this.expanded = true)}>\n ${i18next.t('figure.button.see-the-trend-chart')}\n </button>\n `\n : nothing}\n </section>\n `\n }\n\n /** ๊ทธ๋ฆผ์ ์ ํฌ๊ธฐ๋ก ๋ณด์ฌ ์ค๋ค. ์ข์ผ๋ฉด ์ค์ด์ง ์๊ณ ๋๊ฒจ ๋ณด๊ฒ ๋๋ค. */\n private renderSheet() {\n if (!this.expanded || !this.curve) return nothing\n\n return html`\n <div sheet @click=${() => (this.expanded = false)}>\n <figure @click=${(e: Event) => e.stopPropagation()}>\n ${unsafeSVG(this.curve)}\n <figcaption>\n <button close @click=${() => (this.expanded = false)}>${i18next.t('figure.button.close')}</button>\n </figcaption>\n </figure>\n </div>\n `\n }\n\n /**\n * ๋ฐ๊ฒฌ.\n *\n * ์ค๋ฅ(๋ง๋ ๊ฒ)์ ์๋ฐ(์๋ฆฌ๋ ๊ฒ)์ **๊ฐ๋ ค์** ๋ณด์ฌ ์ค๋ค. ์์ผ๋ฉด ์ ์์๊ฐ ๋ฌด์์\n * ๋ฐ๋์ ๊ณ ์ณ์ผ ํ๋์ง ๋ชจ๋ฅธ๋ค. ์๋ฌด๊ฒ๋ ์์ผ๋ฉด ใ์๋คใ๊ณ ๋งํ๋ค โ ๋น ์๋ฆฌ๋ก ๋๋ฉด\n * ๊ฒ์ฌ๊ฐ ๋์๋์ง ์ ์ ์๋ค.\n */\n private renderFindings() {\n if (this.errors.length === 0 && this.violations.length === 0 && this.sizing.length === 0) {\n return html`\n <section>\n <h3>${i18next.t('figure.label.findings')}</h3>\n <p quiet>${i18next.t('figure.text.no-findings')}</p>\n </section>\n `\n }\n\n return html`\n <section>\n <h3>${i18next.t('figure.label.findings')}</h3>\n <ul findings>\n ${this.sizing.map(\n finding => html`\n <li ?violation=${!finding.blocking}>\n <md-icon>call_split</md-icon>\n <span>${finding.message} ${finding.at ? html`<code at>${finding.at}</code>` : ''}</span>\n </li>\n `\n )}\n ${this.errors.map(\n e => html`\n <li>\n <md-icon>error</md-icon>\n <span>${e.message} ${e.at ? html`<code at>${e.at}</code>` : ''}</span>\n </li>\n `\n )}\n ${this.violations.map(\n v => html`\n <li ?violation=${!v.blocking}>\n <md-icon>${v.blocking ? 'block' : 'info'}</md-icon>\n <span>\n ${v.message}${v.blocking && v.actual !== undefined\n ? html` <code at>${v.actual}</code>`\n : ''}\n </span>\n </li>\n `\n )}\n </ul>\n </section>\n `\n }\n\n /** ์๋ณธ ๋ฐ์ดํฐ๋ฅผ ์ธก์ ํด ๊ฒฐ๊ณผ๋ฅผ ์ํ์ ๋ด๋๋ค. ์
์ ์ ๋ถ figure-model ์ด ํ๋ค. */\n private measure() {\n const source = this.source\n if (!source) {\n this.cost = undefined\n this.score = undefined\n this.many = undefined\n this.capacity = undefined\n this.curve = ''\n this.errors = []\n this.violations = []\n this.sizing = []\n return\n }\n\n /*\n ๋ถํ์ด ์์ผ๋ฉด ํ์ ์ ์์ ํ์ง ์๋๋ค โ ์ด ๊ฒ์ด ์๋ค. ใ๋ฌด์์ ๊ณ ์ณ์ผ ํ๋ใ๊ฐ ์๋๋ผ\n ใ๋ฌด์๋ถํฐ ๋๋ใ์ธ ์ํ์ด๊ณ , ๊ทธ ์๋ด๋ ๋ถํ ๋ชฉ๋ก์ด ์ด๋ฏธ ํ๊ณ ์๋ค.\n */\n this.bare = !source.parts?.length\n if (this.bare) {\n this.cost = undefined\n this.score = undefined\n this.many = undefined\n this.capacity = undefined\n this.curve = ''\n this.errors = []\n this.violations = []\n this.sizing = []\n return\n }\n\n const result = validate(source)\n this.errors = result.errors.map(e => ({ code: e.code, message: e.message, at: e.path }))\n this.violations = result.violations.map(v => ({\n code: v.code,\n message: v.message,\n blocking: blocksRelease(v.code),\n actual: v.actual\n }))\n\n if (this.errors.length > 0) {\n // ํ์์ ์ด๊ฒผ์ผ๋ฉด ์ปดํ์ผ์ด ๋์ง๋ค. ์
์ ๋น์ฐ๊ณ ์ค๋ฅ๋ง ๋ณด์ฌ ์ค๋ค.\n this.cost = undefined\n this.score = undefined\n this.many = undefined\n this.capacity = undefined\n this.curve = ''\n this.sizing = []\n this.dispatchEvent(\n new CustomEvent('verdict-changed', { detail: {}, bubbles: true, composed: true })\n )\n return\n }\n\n const blueprint = compile(source)\n\n /*\n ํฌ๊ธฐ๋ฅผ ๋ฐ๊ฟ ๋ณด๋ ์ผ๊ณฑ ์กฐํฉ. ํ์ ๊ท์น์ `figure-model` ์ `gate.ts` ๊ฐ ์ ํ ๊ฒ์ ๊ทธ๋๋ก\n ์ด๋ค โ ๋ฌด์์ด ๋ง๋ ๊ฒ์ธ์ง ํ๋ฉด์ด ๋ค์ ์ ํ๋ฉด ์๋ฒ์ ๋ค๋ฅธ ๋ง์ ํ๊ฒ ๋๋ค.\n */\n const report = sizingReport(blueprint)\n this.sizing = report.findings.map(finding => ({\n code: finding.code,\n message: finding.message,\n /* ์ซ์๊ฐ ์๋๋ผ ์๋ฆฌ๋ฅผ ๋งํ๋ค โ ๊ฐ๋ผ์ ธ ๋์จ ๋ถํ ์ด๋ฆ์ด ๊ณ ์น ์๋ฆฌ๋ค. */\n at: finding.clumps.map(clump => [...clump].sort().join('+')).join(' | ') || undefined,\n blocking: finding.code === 'sizing-splits'\n }))\n\n this.cost = costOf(blueprint, 100)\n // 1๋ง ๊ฐ๋ figure-model ์ ๋ค์ ๋ฌป๋๋ค โ ํ๋ฉด์ด ๊ณฑ์
์ผ๋ก ์ง์ํ์ง ์๋๋ค.\n this.many = costOf(blueprint, 10000)\n this.score = scoreOf(blueprint)\n this.capacity = capacityOf(this.cost)\n\n // ๊ฐ์๋ฅผ ๋ฐ์ผ๋ก ์๋ฆฐ๋ค. ํญ ์ด๋ฆํ๊ฐ ์ด ๊ฐ์ ๋ณด์ฌ ์ฃผ๋๋ฐ, ๊ฑฐ๊ธฐ์ ๋ค์ ์
ํ๋ฉด\n // ๊ฐ์ ํ์์ด ๋ ์๋ฆฌ์์ ๋ค๋ฅด๊ฒ ๋์ฌ ์ ์๋ค.\n this.dispatchEvent(\n new CustomEvent('verdict-changed', {\n detail: { instances: this.capacity?.instances, grade: this.score?.grade },\n bubbles: true,\n composed: true\n })\n )\n this.curve = costCurveSvg(blueprint)\n }\n}\n"]}
|
|
@@ -6,7 +6,7 @@ import './figure-report.js';
|
|
|
6
6
|
import './figure-settings.js';
|
|
7
7
|
import './figure-history-panel.js';
|
|
8
8
|
import { LitElement } from 'lit';
|
|
9
|
-
import type { FigureSource } from '@hatiolab/figure-model';
|
|
9
|
+
import type { ContractChange, FigureSource } from '@hatiolab/figure-model';
|
|
10
10
|
import type { FigureDraft, PartModel } from './figure-source.js';
|
|
11
11
|
import type { ViewSettings } from './figure-view.js';
|
|
12
12
|
declare const FigureSide_base: (new (...args: any[]) => LitElement) & typeof LitElement;
|
|
@@ -42,6 +42,10 @@ export declare class FigureSide extends FigureSide_base {
|
|
|
42
42
|
draft?: FigureDraft;
|
|
43
43
|
parts: PartModel[];
|
|
44
44
|
source?: FigureSource;
|
|
45
|
+
/** ์ด ๊ณ ์นจ์ด ์ด๋ฏธ ๋์ธ ์ธ์คํด์ค์ ๋ฌด์์ ํ๋(ADR-0063 ๊ฒฐ์ 3). ๋ฐํ ์ ๋ํ์๋ ๋น์ด ์๋ค. */
|
|
46
|
+
contract: ContractChange[];
|
|
47
|
+
/** ๊ฒฌ์ฃผ์ง ๋ชปํ ๊น๋ญ. ์์ผ๋ฉด ํ๋ฉด์ด ใํ์ธํ์ง ๋ชปํ๋คใ๋ก ๋งํ๋ค. */
|
|
48
|
+
contractFailure?: string;
|
|
45
49
|
selected: number;
|
|
46
50
|
/** ์ ์ ํ๋ฉด์ ๋ณด๊ธฐ ์ค์ . ์์ฐ์ด ์๋๋ผ ์์
๋๋ค โ ์ ์ฅ๋์ง ์๋๋ค. */
|
|
47
51
|
view: ViewSettings;
|
|
@@ -41,6 +41,8 @@ let FigureSide = class FigureSide extends localize(i18next)(LitElement) {
|
|
|
41
41
|
this.figureVersion = 0;
|
|
42
42
|
this.dirty = false;
|
|
43
43
|
this.parts = [];
|
|
44
|
+
/** ์ด ๊ณ ์นจ์ด ์ด๋ฏธ ๋์ธ ์ธ์คํด์ค์ ๋ฌด์์ ํ๋(ADR-0063 ๊ฒฐ์ 3). ๋ฐํ ์ ๋ํ์๋ ๋น์ด ์๋ค. */
|
|
45
|
+
this.contract = [];
|
|
44
46
|
this.selected = -1;
|
|
45
47
|
/** ์ ์ ํ๋ฉด์ ๋ณด๊ธฐ ์ค์ . ์์ฐ์ด ์๋๋ผ ์์
๋๋ค โ ์ ์ฅ๋์ง ์๋๋ค. */
|
|
46
48
|
this.view = DEFAULT_VIEW;
|
|
@@ -177,6 +179,8 @@ let FigureSide = class FigureSide extends localize(i18next)(LitElement) {
|
|
|
177
179
|
.figureTags=${this.figureTags}
|
|
178
180
|
.draft=${this.draft}
|
|
179
181
|
.parts=${this.parts}
|
|
182
|
+
.contract=${this.contract}
|
|
183
|
+
.contractFailure=${this.contractFailure}
|
|
180
184
|
.selected=${this.selected}
|
|
181
185
|
></figure-inspector>
|
|
182
186
|
|
|
@@ -276,6 +280,14 @@ __decorate([
|
|
|
276
280
|
property({ type: Object }),
|
|
277
281
|
__metadata("design:type", Object)
|
|
278
282
|
], FigureSide.prototype, "source", void 0);
|
|
283
|
+
__decorate([
|
|
284
|
+
property({ type: Array }),
|
|
285
|
+
__metadata("design:type", Array)
|
|
286
|
+
], FigureSide.prototype, "contract", void 0);
|
|
287
|
+
__decorate([
|
|
288
|
+
property({ type: String }),
|
|
289
|
+
__metadata("design:type", String)
|
|
290
|
+
], FigureSide.prototype, "contractFailure", void 0);
|
|
279
291
|
__decorate([
|
|
280
292
|
property({ type: Number }),
|
|
281
293
|
__metadata("design:type", Object)
|