design: adopt Open Props tokens, indigo accent + IBM Plex Sans, collision colour
- Add Open Props as the token foundation (@import "open-props/style"). Our semantic tokens (--bg/--surface/--border/--text/--shadow-*/--transition) are now backed by its gray ramp, shadows and easing; the rest of the CSS is untouched since it already references var(--…). - Accent → indigo #4f46e5 (--accent + derived rings / month-hover), and the timeline bar default colours (appearance.ts) move to the same indigo so the content and UI share one palette. - Font → IBM Plex Sans, self-hosted via @fontsource (latin + cyrillic, weights 400/500/600/700) so there is no runtime Google Fonts dependency. Backed into --font-sans (overrides Open Props' :where() default). Tabular figures on the counters and map legend. - Collision default colour → warm amber-orange #e8590c: distinct from the indigo bars and from the green/red map status, reads as a conflict warning. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
parent
de0c369bb5
commit
17c54db501
17
frontend/package-lock.json
generated
17
frontend/package-lock.json
generated
@ -8,6 +8,8 @@
|
||||
"name": "mapdash-frontend",
|
||||
"version": "0.1.0",
|
||||
"dependencies": {
|
||||
"@fontsource/ibm-plex-sans": "^5.3.0",
|
||||
"open-props": "^1.7.23",
|
||||
"vis-data": "^7.1.9",
|
||||
"vis-timeline": "^7.7.3"
|
||||
},
|
||||
@ -420,6 +422,15 @@
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/@fontsource/ibm-plex-sans": {
|
||||
"version": "5.3.0",
|
||||
"resolved": "https://registry.npmjs.org/@fontsource/ibm-plex-sans/-/ibm-plex-sans-5.3.0.tgz",
|
||||
"integrity": "sha512-CbE4CbbEEZJX860XyUiRpsksXIQR8Rp2XDva2VO53NJox9tVNtusrysd2x5YkUEY3ErQ66W1IiiQL8/wihhw5w==",
|
||||
"license": "OFL-1.1",
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/ayuhito"
|
||||
}
|
||||
},
|
||||
"node_modules/@rollup/rollup-android-arm-eabi": {
|
||||
"version": "4.62.2",
|
||||
"resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.62.2.tgz",
|
||||
@ -898,6 +909,12 @@
|
||||
"node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1"
|
||||
}
|
||||
},
|
||||
"node_modules/open-props": {
|
||||
"version": "1.7.23",
|
||||
"resolved": "https://registry.npmjs.org/open-props/-/open-props-1.7.23.tgz",
|
||||
"integrity": "sha512-+xyrJmxV9QUBFbSwPROYhOg/FLXry+uuPr4R+B5EaE4556Oc18/8ZC/fL5A+/lbRSwNvA0Alh+C0KpyFWLmLZg==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/picocolors": {
|
||||
"version": "1.1.1",
|
||||
"resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.1.1.tgz",
|
||||
|
||||
@ -9,6 +9,8 @@
|
||||
"build": "tsc --noEmit && vite build"
|
||||
},
|
||||
"dependencies": {
|
||||
"@fontsource/ibm-plex-sans": "^5.3.0",
|
||||
"open-props": "^1.7.23",
|
||||
"vis-data": "^7.1.9",
|
||||
"vis-timeline": "^7.7.3"
|
||||
},
|
||||
|
||||
@ -22,20 +22,20 @@ const LS_KEY = 'mapdash.appearance.v1';
|
||||
|
||||
/** Sensible out-of-the-box colours for the known statuses. */
|
||||
export const DEFAULT_STATUS_COLORS: Record<string, string> = {
|
||||
'РК. Новая': '#2e66d6',
|
||||
'РК. Размещено': '#2e66d6',
|
||||
'РК. Макет РИМ согласован': '#2e66d6',
|
||||
'РК. Ожидает монтаж': '#2e66d6',
|
||||
'РК. Ожидает демонтаж': '#2e66d6',
|
||||
'РК. Ожидает перемонтаж': '#2e66d6',
|
||||
'РК. Архив': '#2e66d6',
|
||||
'РК. Новая': '#4f46e5',
|
||||
'РК. Размещено': '#4f46e5',
|
||||
'РК. Макет РИМ согласован': '#4f46e5',
|
||||
'РК. Ожидает монтаж': '#4f46e5',
|
||||
'РК. Ожидает демонтаж': '#4f46e5',
|
||||
'РК. Ожидает перемонтаж': '#4f46e5',
|
||||
'РК. Архив': '#4f46e5',
|
||||
};
|
||||
|
||||
export function defaultAppearance(): Appearance {
|
||||
return {
|
||||
colors: { ...DEFAULT_STATUS_COLORS },
|
||||
collisionColor: '#BA55D3',
|
||||
defaultColor: '#2e66d6',
|
||||
collisionColor: '#e8590c',
|
||||
defaultColor: '#4f46e5',
|
||||
rowHeightPx: 30,
|
||||
barHeightPct: 62,
|
||||
barFontPx: 11,
|
||||
|
||||
@ -1,3 +1,13 @@
|
||||
// IBM Plex Sans — self-hosted (no runtime Google Fonts dependency), latin + cyrillic.
|
||||
import '@fontsource/ibm-plex-sans/400.css';
|
||||
import '@fontsource/ibm-plex-sans/500.css';
|
||||
import '@fontsource/ibm-plex-sans/600.css';
|
||||
import '@fontsource/ibm-plex-sans/700.css';
|
||||
import '@fontsource/ibm-plex-sans/cyrillic-400.css';
|
||||
import '@fontsource/ibm-plex-sans/cyrillic-500.css';
|
||||
import '@fontsource/ibm-plex-sans/cyrillic-600.css';
|
||||
import '@fontsource/ibm-plex-sans/cyrillic-700.css';
|
||||
|
||||
import './styles.css';
|
||||
import 'vis-timeline/styles/vis-timeline-graph2d.min.css';
|
||||
|
||||
|
||||
@ -28,7 +28,7 @@ function donutSvg(total: number, busy: number): string {
|
||||
`<circle cx="${m}" cy="${m}" r="${r}" fill="none" stroke="${CLUSTER_BUSY}" stroke-width="${sw}" ` +
|
||||
`stroke-dasharray="${busyLen.toFixed(1)} ${c.toFixed(1)}" transform="rotate(-90 ${m} ${m})"/>` +
|
||||
`<text x="${m}" y="${m}" text-anchor="middle" dominant-baseline="central" ` +
|
||||
`font-family="-apple-system,Segoe UI,Roboto,Arial,sans-serif" font-size="14" font-weight="700" fill="#1f2430">${total}</text>` +
|
||||
`font-family="'IBM Plex Sans',sans-serif" font-size="14" font-weight="700" fill="#1f2430">${total}</text>` +
|
||||
`</svg>`
|
||||
);
|
||||
}
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
/* Open Props — design-token foundation (colours, shadows, easing, scales).
|
||||
Our semantic tokens below are backed by its ramps, so the rest of the CSS
|
||||
(which references var(--accent) etc.) is untouched. */
|
||||
@import "open-props/style";
|
||||
|
||||
:root {
|
||||
/* appearance (overridden at runtime by appearance.ts) */
|
||||
--row-h: 30px;
|
||||
@ -6,32 +11,33 @@
|
||||
--label-font: 12px;
|
||||
--label-w: 340px;
|
||||
|
||||
/* ---- design tokens (light) ---- */
|
||||
/* ---- design tokens (light), backed by Open Props ---- */
|
||||
--bg: #ffffff;
|
||||
--surface: #f7f8fa;
|
||||
--surface-2: #eef1f5;
|
||||
--border: #e5e7eb;
|
||||
--border-strong: #d1d6de;
|
||||
--text: #1f2430;
|
||||
--text-muted: #6b7280;
|
||||
--accent: #2e66d6;
|
||||
--accent-weak: rgba(46, 102, 214, .12);
|
||||
--accent-ring: rgba(46, 102, 214, .20);
|
||||
--surface: var(--gray-0);
|
||||
--surface-2: var(--gray-1);
|
||||
--border: var(--gray-3);
|
||||
--border-strong: var(--gray-4);
|
||||
--text: var(--gray-9);
|
||||
--text-muted: var(--gray-6);
|
||||
--font-sans: "IBM Plex Sans", -apple-system, "Segoe UI", Roboto, Arial, sans-serif;
|
||||
--accent: #4f46e5;
|
||||
--accent-weak: rgba(79, 70, 229, .12);
|
||||
--accent-ring: rgba(79, 70, 229, .22);
|
||||
--radius: 8px;
|
||||
--radius-sm: 6px;
|
||||
--shadow-sm: 0 1px 2px rgba(16, 24, 40, .06);
|
||||
--shadow-md: 0 6px 18px rgba(16, 24, 40, .12);
|
||||
--transition: .13s ease;
|
||||
--shadow-sm: var(--shadow-1);
|
||||
--shadow-md: var(--shadow-3);
|
||||
--transition: .13s var(--ease-3);
|
||||
|
||||
/* timeline / map surfaces (built on the tokens above) */
|
||||
--grid-line: var(--border);
|
||||
--row-even: #f5f6f8;
|
||||
--row-even: var(--gray-1);
|
||||
--row-odd: #ffffff;
|
||||
--row-hover: #fff3cd;
|
||||
--month-hover: rgba(46, 102, 214, .08);
|
||||
--tip-bg: #1f2430;
|
||||
--month-hover: rgba(79, 70, 229, .08);
|
||||
--tip-bg: var(--gray-9);
|
||||
--tip-text: #ffffff;
|
||||
--tip-sub: #cfd3d6;
|
||||
--tip-sub: var(--gray-4);
|
||||
--today: #ef5350;
|
||||
}
|
||||
|
||||
@ -62,7 +68,7 @@ html, body { height: 100%; margin: 0; overflow: hidden; }
|
||||
body {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
font-family: -apple-system, "Segoe UI", Roboto, Arial, sans-serif;
|
||||
font-family: var(--font-sans);
|
||||
background: var(--bg);
|
||||
color: var(--text);
|
||||
}
|
||||
@ -176,7 +182,7 @@ input::placeholder { color: var(--text-muted); }
|
||||
margin-top: auto; padding: 8px 12px;
|
||||
background: var(--surface-2); border: none;
|
||||
border-radius: var(--radius-sm); font-size: 12px; color: var(--text-muted);
|
||||
line-height: 1.5; white-space: nowrap;
|
||||
line-height: 1.5; white-space: nowrap; font-variant-numeric: tabular-nums;
|
||||
}
|
||||
|
||||
/* Scale group: stack the "Оформление" button under the zoom slider. */
|
||||
@ -345,7 +351,7 @@ input::placeholder { color: var(--text-muted); }
|
||||
background: var(--bg); border: 1px solid var(--border); border-radius: var(--radius);
|
||||
padding: 8px 12px; font-size: 12px; color: var(--text);
|
||||
display: flex; flex-direction: column; align-items: flex-start; gap: 5px;
|
||||
box-shadow: var(--shadow-md);
|
||||
box-shadow: var(--shadow-md); font-variant-numeric: tabular-nums;
|
||||
}
|
||||
#map-legend .lg-item { display: inline-flex; align-items: center; gap: 6px; white-space: nowrap; font-size: 12px; }
|
||||
#map-legend #map-counter { padding-left: 18px; } /* align "всего" with the dotted rows */
|
||||
|
||||
Loading…
Reference in New Issue
Block a user