@neo4j-ndl/react 4.18.8 → 4.18.9

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.
@@ -114,7 +114,8 @@ function parseTimeString(s) {
114
114
  * e.g. `"2024-01-01"`, `"2024-01-01T14:30:00"`, `"2024-01-01T14:30:00.500"`
115
115
  *
116
116
  * Strings with a time component that lack `Z`, an offset, or an IANA bracket are
117
- * parsed as UTC wall-clock time (same semantics as Neo4j `LocalDateTime`).
117
+ * parsed as UTC wall-clock time. (Neo4j `LocalDateTime` values should instead be
118
+ * parsed with {@link parseLocalDateString}, in the browser's local timezone.)
118
119
  */
119
120
  function parseDateString(s) {
120
121
  // RFC 9557 / ZonedDateTime with IANA bracket notation
@@ -1 +1 @@
1
- {"version":3,"file":"date-utils.js","sourceRoot":"","sources":["../../../../src/_generated/style-rules/date-utils.ts"],"names":[],"mappings":"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","sourcesContent":["/*\n * AUTO-GENERATED FILE — DO NOT EDIT.\n * Source of truth: packages/style-rules/src/\n * Regenerate with `pnpm generate:shared` (runs automatically at build/dev/install).\n */\n\n/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport { Temporal } from 'temporal-polyfill';\n\nconst MS_PER_DAY = 86_400_000;\n\nfunction plainTimeToMs(pt: Temporal.PlainTime): number {\n return (\n pt.hour * 3_600_000 +\n pt.minute * 60_000 +\n pt.second * 1_000 +\n pt.millisecond\n );\n}\n\nfunction parseOffsetMs(offsetStr: string): number | null {\n const match = offsetStr.match(/^([+-])(\\d{2}):(\\d{2})$/);\n if (!match) {\n return null;\n }\n const sign = match[1] === '+' ? 1 : -1;\n return (\n sign *\n (parseInt(match[2], 10) * 3_600_000 + parseInt(match[3], 10) * 60_000)\n );\n}\n\n/**\n * Parses an ISO 8601 time string to UTC milliseconds since midnight\n * (0–86,399,999). Returns `null` if the string cannot be parsed.\n *\n * Three formats are accepted:\n * 1. Local time (no offset): `\"14:30:00\"`, `\"14:30:00.500\"` — treated as UTC\n * 2. UTC time with Z suffix: `\"14:30:00Z\"` — treated identically to the local form\n * 3. Offset time: `\"14:30:00+02:00\"` — the offset is applied so the result\n * is the equivalent UTC time of day. `\"12:00:00+01:00\"` resolves to\n * 39,600,000 (11:00 UTC), which is less than `\"12:00:00+00:00\"` (43,200,000).\n *\n * Values wrap around midnight: `\"00:00:00+01:00\"` → 82,800,000 (23:00 UTC).\n */\nexport function parseTimeString(s: string): number | null {\n // Reject datetime strings and anything with an IANA timezone bracket.\n // Temporal.PlainTime.from silently extracts the time portion from strings\n // containing a 'T' separator. IANA brackets are meaningless for time-only\n // values (there is no date to anchor DST to), so they are also rejected.\n if (s.includes('T') || s.includes('[')) {\n return null;\n }\n // Offset time: detect \"+HH:MM\" or \"-HH:MM\" suffix first. Temporal.PlainTime.from\n // silently strips offsets and returns the clock-face time, so we must handle\n // offset strings explicitly before falling through to the plain parse.\n const offsetMatch = s.match(/([+-]\\d{2}:\\d{2})(\\[.*\\])?$/);\n if (offsetMatch) {\n const offsetStr = offsetMatch[1];\n const timeStr = s.slice(0, s.indexOf(offsetStr));\n const offsetMs = parseOffsetMs(offsetStr);\n if (offsetMs !== null) {\n try {\n const localMs = plainTimeToMs(Temporal.PlainTime.from(timeStr));\n // Subtract the UTC offset to normalise to UTC time-of-day; wrap around midnight\n return (((localMs - offsetMs) % MS_PER_DAY) + MS_PER_DAY) % MS_PER_DAY;\n } catch {\n /* empty */\n }\n }\n return null;\n }\n\n // UTC time with Z suffix (e.g. \"14:30:00Z\") — strip Z and treat as local (UTC) time.\n // Only apply when there is no 'T' in the string; a datetime string like\n // \"2024-06-15T14:30:00Z\" must not be accepted here.\n const normalized = s.endsWith('Z') && !s.includes('T') ? s.slice(0, -1) : s;\n\n // Local time (no offset) — treated as UTC\n try {\n return plainTimeToMs(Temporal.PlainTime.from(normalized));\n } catch {\n /* empty */\n }\n\n return null;\n}\n\n/**\n * Parses an ISO 8601 or RFC 9557 date/datetime string to a Unix millisecond\n * timestamp. Returns `null` if the string cannot be parsed.\n *\n * Three formats are tried in order:\n * 1. RFC 9557 ZonedDateTime with IANA bracket notation\n * e.g. `\"2024-06-15T14:00:00[Europe/Stockholm]\"` (offset inferred from the\n * named timezone, including DST) or `\"2024-06-15T14:00:00+02:00[Europe/Stockholm]\"`\n * (offset explicit; bracket must agree with the IANA zone)\n * 2. UTC or fixed-offset Instant\n * e.g. `\"2024-01-01T00:00:00Z\"`, `\"2024-01-01T00:00:00+02:00\"`\n * 3. Plain date or datetime (no offset, `Z`, or IANA bracket), interpreted as UTC\n * e.g. `\"2024-01-01\"`, `\"2024-01-01T14:30:00\"`, `\"2024-01-01T14:30:00.500\"`\n *\n * Strings with a time component that lack `Z`, an offset, or an IANA bracket are\n * parsed as UTC wall-clock time (same semantics as Neo4j `LocalDateTime`).\n */\nexport function parseDateString(s: string): number | null {\n // RFC 9557 / ZonedDateTime with IANA bracket notation\n try {\n return Temporal.ZonedDateTime.from(s).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n // UTC or fixed-offset datetime (no IANA name)\n try {\n return Temporal.Instant.from(s).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n // Plain datetime — interpret as UTC.\n // Also covers date-only strings like \"2024-01-01\" (PlainDateTime.from parses\n // them as midnight), so a separate PlainDate path is not needed.\n try {\n return Temporal.PlainDateTime.from(s).toZonedDateTime('UTC')\n .epochMilliseconds;\n } catch {\n /* empty */\n }\n\n return null;\n}\n\n/**\n * Parses a plain (unzoned) ISO 8601 date or datetime string to a Unix\n * millisecond timestamp, interpreting the wall-clock time in the given\n * `timeZone` (defaults to the browser's local timezone via\n * `Temporal.Now.timeZoneId()`). Returns `null` if the string cannot be\n * parsed or contains any timezone qualifier.\n *\n * Only plain date/datetime strings are accepted — strings with `Z`, a\n * fixed UTC offset (`+02:00`), or an IANA bracket (`[Europe/Stockholm]`)\n * are **rejected** and return `null`. This mirrors the semantics of\n * Neo4j `LocalDateTime`, which has no associated timezone.\n *\n * Accepted formats:\n * - Plain datetime: `\"2024-01-01T14:30:00\"`, `\"2024-01-01T14:30:00.500\"`\n * - Date-only (treated as local midnight): `\"2024-01-01\"`\n *\n * The optional `timeZone` parameter overrides the browser's local timezone,\n * which is useful for deterministic testing.\n */\nexport function parseLocalDateString(\n s: string,\n timeZone?: string,\n): number | null {\n // Reject strings that carry explicit timezone information. This mirrors the\n // cascade in parseDateString but uses successful parsing as a rejection\n // signal rather than an acceptance signal:\n //\n // - ZonedDateTime.from succeeds → string has an IANA bracket → reject\n // - Instant.from succeeds → string has Z or a fixed offset → reject\n // - PlainDateTime.from succeeds → truly plain string → accept\n //\n // The polyfill's PlainDateTime.from() silently strips offsets/brackets\n // instead of throwing, so these two pre-checks are necessary to enforce\n // the plain-only constraint.\n try {\n Temporal.ZonedDateTime.from(s);\n return null;\n } catch {\n /* not a zoned datetime — continue */\n }\n\n try {\n Temporal.Instant.from(s);\n return null;\n } catch {\n /* not a UTC/offset instant — continue */\n }\n\n const tz = timeZone ?? Temporal.Now.timeZoneId();\n try {\n return Temporal.PlainDateTime.from(s).toZonedDateTime(tz).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n return null;\n}\n"]}
1
+ {"version":3,"file":"date-utils.js","sourceRoot":"","sources":["../../../../src/_generated/style-rules/date-utils.ts"],"names":[],"mappings":"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","sourcesContent":["/*\n * AUTO-GENERATED FILE — DO NOT EDIT.\n * Source of truth: packages/style-rules/src/\n * Regenerate with `pnpm generate:shared` (runs automatically at build/dev/install).\n */\n\n/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport { Temporal } from 'temporal-polyfill';\n\nconst MS_PER_DAY = 86_400_000;\n\nfunction plainTimeToMs(pt: Temporal.PlainTime): number {\n return (\n pt.hour * 3_600_000 +\n pt.minute * 60_000 +\n pt.second * 1_000 +\n pt.millisecond\n );\n}\n\nfunction parseOffsetMs(offsetStr: string): number | null {\n const match = offsetStr.match(/^([+-])(\\d{2}):(\\d{2})$/);\n if (!match) {\n return null;\n }\n const sign = match[1] === '+' ? 1 : -1;\n return (\n sign *\n (parseInt(match[2], 10) * 3_600_000 + parseInt(match[3], 10) * 60_000)\n );\n}\n\n/**\n * Parses an ISO 8601 time string to UTC milliseconds since midnight\n * (0–86,399,999). Returns `null` if the string cannot be parsed.\n *\n * Three formats are accepted:\n * 1. Local time (no offset): `\"14:30:00\"`, `\"14:30:00.500\"` — treated as UTC\n * 2. UTC time with Z suffix: `\"14:30:00Z\"` — treated identically to the local form\n * 3. Offset time: `\"14:30:00+02:00\"` — the offset is applied so the result\n * is the equivalent UTC time of day. `\"12:00:00+01:00\"` resolves to\n * 39,600,000 (11:00 UTC), which is less than `\"12:00:00+00:00\"` (43,200,000).\n *\n * Values wrap around midnight: `\"00:00:00+01:00\"` → 82,800,000 (23:00 UTC).\n */\nexport function parseTimeString(s: string): number | null {\n // Reject datetime strings and anything with an IANA timezone bracket.\n // Temporal.PlainTime.from silently extracts the time portion from strings\n // containing a 'T' separator. IANA brackets are meaningless for time-only\n // values (there is no date to anchor DST to), so they are also rejected.\n if (s.includes('T') || s.includes('[')) {\n return null;\n }\n // Offset time: detect \"+HH:MM\" or \"-HH:MM\" suffix first. Temporal.PlainTime.from\n // silently strips offsets and returns the clock-face time, so we must handle\n // offset strings explicitly before falling through to the plain parse.\n const offsetMatch = s.match(/([+-]\\d{2}:\\d{2})(\\[.*\\])?$/);\n if (offsetMatch) {\n const offsetStr = offsetMatch[1];\n const timeStr = s.slice(0, s.indexOf(offsetStr));\n const offsetMs = parseOffsetMs(offsetStr);\n if (offsetMs !== null) {\n try {\n const localMs = plainTimeToMs(Temporal.PlainTime.from(timeStr));\n // Subtract the UTC offset to normalise to UTC time-of-day; wrap around midnight\n return (((localMs - offsetMs) % MS_PER_DAY) + MS_PER_DAY) % MS_PER_DAY;\n } catch {\n /* empty */\n }\n }\n return null;\n }\n\n // UTC time with Z suffix (e.g. \"14:30:00Z\") — strip Z and treat as local (UTC) time.\n // Only apply when there is no 'T' in the string; a datetime string like\n // \"2024-06-15T14:30:00Z\" must not be accepted here.\n const normalized = s.endsWith('Z') && !s.includes('T') ? s.slice(0, -1) : s;\n\n // Local time (no offset) — treated as UTC\n try {\n return plainTimeToMs(Temporal.PlainTime.from(normalized));\n } catch {\n /* empty */\n }\n\n return null;\n}\n\n/**\n * Parses an ISO 8601 or RFC 9557 date/datetime string to a Unix millisecond\n * timestamp. Returns `null` if the string cannot be parsed.\n *\n * Three formats are tried in order:\n * 1. RFC 9557 ZonedDateTime with IANA bracket notation\n * e.g. `\"2024-06-15T14:00:00[Europe/Stockholm]\"` (offset inferred from the\n * named timezone, including DST) or `\"2024-06-15T14:00:00+02:00[Europe/Stockholm]\"`\n * (offset explicit; bracket must agree with the IANA zone)\n * 2. UTC or fixed-offset Instant\n * e.g. `\"2024-01-01T00:00:00Z\"`, `\"2024-01-01T00:00:00+02:00\"`\n * 3. Plain date or datetime (no offset, `Z`, or IANA bracket), interpreted as UTC\n * e.g. `\"2024-01-01\"`, `\"2024-01-01T14:30:00\"`, `\"2024-01-01T14:30:00.500\"`\n *\n * Strings with a time component that lack `Z`, an offset, or an IANA bracket are\n * parsed as UTC wall-clock time. (Neo4j `LocalDateTime` values should instead be\n * parsed with {@link parseLocalDateString}, in the browser's local timezone.)\n */\nexport function parseDateString(s: string): number | null {\n // RFC 9557 / ZonedDateTime with IANA bracket notation\n try {\n return Temporal.ZonedDateTime.from(s).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n // UTC or fixed-offset datetime (no IANA name)\n try {\n return Temporal.Instant.from(s).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n // Plain datetime — interpret as UTC.\n // Also covers date-only strings like \"2024-01-01\" (PlainDateTime.from parses\n // them as midnight), so a separate PlainDate path is not needed.\n try {\n return Temporal.PlainDateTime.from(s).toZonedDateTime('UTC')\n .epochMilliseconds;\n } catch {\n /* empty */\n }\n\n return null;\n}\n\n/**\n * Parses a plain (unzoned) ISO 8601 date or datetime string to a Unix\n * millisecond timestamp, interpreting the wall-clock time in the given\n * `timeZone` (defaults to the browser's local timezone via\n * `Temporal.Now.timeZoneId()`). Returns `null` if the string cannot be\n * parsed or contains any timezone qualifier.\n *\n * Only plain date/datetime strings are accepted — strings with `Z`, a\n * fixed UTC offset (`+02:00`), or an IANA bracket (`[Europe/Stockholm]`)\n * are **rejected** and return `null`. This mirrors the semantics of\n * Neo4j `LocalDateTime`, which has no associated timezone.\n *\n * Accepted formats:\n * - Plain datetime: `\"2024-01-01T14:30:00\"`, `\"2024-01-01T14:30:00.500\"`\n * - Date-only (treated as local midnight): `\"2024-01-01\"`\n *\n * The optional `timeZone` parameter overrides the browser's local timezone,\n * which is useful for deterministic testing.\n */\nexport function parseLocalDateString(\n s: string,\n timeZone?: string,\n): number | null {\n // Reject strings that carry explicit timezone information. This mirrors the\n // cascade in parseDateString but uses successful parsing as a rejection\n // signal rather than an acceptance signal:\n //\n // - ZonedDateTime.from succeeds → string has an IANA bracket → reject\n // - Instant.from succeeds → string has Z or a fixed offset → reject\n // - PlainDateTime.from succeeds → truly plain string → accept\n //\n // The polyfill's PlainDateTime.from() silently strips offsets/brackets\n // instead of throwing, so these two pre-checks are necessary to enforce\n // the plain-only constraint.\n try {\n Temporal.ZonedDateTime.from(s);\n return null;\n } catch {\n /* not a zoned datetime — continue */\n }\n\n try {\n Temporal.Instant.from(s);\n return null;\n } catch {\n /* not a UTC/offset instant — continue */\n }\n\n const tz = timeZone ?? Temporal.Now.timeZoneId();\n try {\n return Temporal.PlainDateTime.from(s).toZonedDateTime(tz).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n return null;\n}\n"]}
@@ -116,6 +116,28 @@ const styleRules = [
116
116
  ],
117
117
  },
118
118
  },
119
+ // Accessible default text color: a background is set but no textColor, so an
120
+ // accessible text color is chosen automatically for contrast against the
121
+ // dark background. Compare the cypherCommand cell here with the one below,
122
+ // which uses the same background but an explicit (low-contrast) textColor.
123
+ {
124
+ apply: { color: { value: '#1e3a5f' } },
125
+ column: 'cypherCommand',
126
+ priority: 1,
127
+ where: { equal: [{ column: 'name' }, 'Ken Kessler'] },
128
+ },
129
+ // Explicit textColor always wins: even a low-contrast text color is left
130
+ // untouched -- the automatic accessible default only fills in when no
131
+ // textColor/textColorRange resolved one.
132
+ {
133
+ apply: {
134
+ color: { value: '#1e3a5f' },
135
+ textColor: { value: '#fca5a5' },
136
+ },
137
+ column: 'cypherCommand',
138
+ priority: 1,
139
+ where: { equal: [{ column: 'name' }, 'Jonathon Graham'] },
140
+ },
119
141
  ];
120
142
  const Component = () => {
121
143
  const columnHelper = (0, react_table_1.createColumnHelper)();
@@ -1 +1 @@
1
- {"version":3,"file":"datagrid-rule-based-styling.story.js","sourceRoot":"","sources":["../../../../src/data-grid/stories/datagrid-rule-based-styling.story.tsx"],"names":[],"mappings":"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","sourcesContent":["/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport '@neo4j-ndl/base/lib/neo4j-ds-styles.css';\n\nimport { DataGrid } from '@neo4j-ndl/react';\nimport {\n createColumnHelper,\n getCoreRowModel,\n getPaginationRowModel,\n getSortedRowModel,\n useReactTable,\n} from '@tanstack/react-table';\n\nimport { type DataGridStyleRule } from '../style-rules/types';\nimport { TABLE_DEMO_DATA, type TestDataFormat } from './staticData';\n\ntype BigintTestDataFormat = TestDataFormat & { preciseId: bigint };\n\nconst BIGINT_ID_START = BigInt('9007199254740993');\nconst tableData: BigintTestDataFormat[] = TABLE_DEMO_DATA.map((row, index) => ({\n ...row,\n preciseId: BIGINT_ID_START + BigInt(index),\n}));\n\nconst styleRules: DataGridStyleRule[] = [\n // Row coloring: all cells styled when name contains \"Alicia\"\n {\n apply: {\n color: { value: '#000000' },\n textColor: { value: '#ffffff' },\n },\n column: null,\n priority: 3,\n where: { contains: [{ column: 'name' }, 'Alicia'] },\n },\n // Cell coloring: cells in the \"age\" column with value 51 get green\n {\n apply: { color: { value: '#00bb00' } },\n column: 'age',\n priority: 3,\n where: { equal: [{ column: 'age' }, 51] },\n },\n // Dual color ranges on the \"age\" column: independent gradients for background\n // (driven by age, full 0-100 range) and text color (driven by age too, but\n // with a narrower 20-80 band so the text contrast is calibrated separately).\n {\n apply: {\n colorRange: {\n maxColor: '#f00000',\n maxValue: 100,\n midColor: '#a00000',\n midValue: 50,\n minColor: '#800000',\n minValue: 0,\n onColumn: 'age',\n },\n textColorRange: {\n maxColor: '#aaaaaa',\n maxValue: 80,\n minColor: '#ffffff',\n minValue: 20,\n onColumn: 'age',\n },\n },\n column: 'age',\n priority: 2, // Lower priority so explicit green rule overrides\n },\n // Multi-column rule: all cells styled when age > 50 AND name contains \"o\"\n {\n apply: {\n color: { value: '#fef3c7' },\n textColor: { value: '#000000' },\n },\n column: null,\n priority: 0, // Lower priority so other rules take precedence\n where: {\n and: [\n { greaterThan: [{ column: 'age' }, 50] },\n { contains: [{ column: 'name' }, 'o'] },\n ],\n },\n },\n // Bigint range: adjacent values above Number.MAX_SAFE_INTEGER retain their\n // precision. Wrapped literals are JSON-safe; BigInt(...) is programmatic.\n {\n apply: {\n colorRange: {\n maxColor: '#7c3aed',\n maxValue: BIGINT_ID_START + BigInt(tableData.length - 1),\n minColor: '#ede9fe',\n minValue: { bigint: BIGINT_ID_START.toString() },\n onColumn: 'preciseId',\n },\n textColor: { value: '#111827' },\n },\n column: 'preciseId',\n priority: 1,\n },\n // Exact bigint comparison using the JSON-safe literal form.\n {\n apply: {\n color: { value: '#4c1d95' },\n textColor: { value: '#ffffff' },\n },\n column: 'preciseId',\n priority: 2,\n where: {\n equal: [\n { column: 'preciseId' },\n { bigint: (BIGINT_ID_START + BigInt(2)).toString() },\n ],\n },\n },\n];\n\nconst Component = () => {\n const columnHelper = createColumnHelper<BigintTestDataFormat>();\n\n const columns = [\n columnHelper.accessor('name', {\n cell: (info) => info.getValue(),\n header: () => 'Name',\n minSize: 180,\n size: 220,\n }),\n columnHelper.accessor('age', {\n cell: (info) => info.renderValue(),\n header: () => 'Age',\n minSize: 80,\n }),\n columnHelper.accessor('preciseId', {\n cell: (info) => info.getValue().toString(),\n header: () => 'Bigint ID',\n minSize: 180,\n size: 180,\n }),\n columnHelper.accessor('cypherCommand', {\n cell: (info) => info.getValue(),\n header: () => 'Cypher Command',\n minSize: 400,\n size: 400,\n }),\n ];\n\n const table = useReactTable({\n columnResizeMode: 'onChange',\n columns,\n data: tableData,\n defaultColumn: {\n maxSize: 800,\n minSize: 80,\n },\n enableSorting: true,\n getCoreRowModel: getCoreRowModel(),\n getPaginationRowModel: getPaginationRowModel(),\n getSortedRowModel: getSortedRowModel(),\n initialState: {\n pagination: {\n pageSize: 10,\n },\n },\n });\n\n return (\n <div className=\"n-w-full n-bg-light-neutral-text-weakest\">\n <DataGrid\n isResizable={false}\n tableInstance={table}\n isKeyboardNavigable={false}\n styleRules={styleRules}\n styling={{\n borderStyle: 'all-sides',\n hasHoverEffects: true,\n hasZebraStriping: false,\n }}\n />\n </div>\n );\n};\n\nexport default Component;\n"]}
1
+ {"version":3,"file":"datagrid-rule-based-styling.story.js","sourceRoot":"","sources":["../../../../src/data-grid/stories/datagrid-rule-based-styling.story.tsx"],"names":[],"mappings":"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","sourcesContent":["/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport '@neo4j-ndl/base/lib/neo4j-ds-styles.css';\n\nimport { DataGrid } from '@neo4j-ndl/react';\nimport {\n createColumnHelper,\n getCoreRowModel,\n getPaginationRowModel,\n getSortedRowModel,\n useReactTable,\n} from '@tanstack/react-table';\n\nimport { type DataGridStyleRule } from '../style-rules/types';\nimport { TABLE_DEMO_DATA, type TestDataFormat } from './staticData';\n\ntype BigintTestDataFormat = TestDataFormat & { preciseId: bigint };\n\nconst BIGINT_ID_START = BigInt('9007199254740993');\nconst tableData: BigintTestDataFormat[] = TABLE_DEMO_DATA.map((row, index) => ({\n ...row,\n preciseId: BIGINT_ID_START + BigInt(index),\n}));\n\nconst styleRules: DataGridStyleRule[] = [\n // Row coloring: all cells styled when name contains \"Alicia\"\n {\n apply: {\n color: { value: '#000000' },\n textColor: { value: '#ffffff' },\n },\n column: null,\n priority: 3,\n where: { contains: [{ column: 'name' }, 'Alicia'] },\n },\n // Cell coloring: cells in the \"age\" column with value 51 get green\n {\n apply: { color: { value: '#00bb00' } },\n column: 'age',\n priority: 3,\n where: { equal: [{ column: 'age' }, 51] },\n },\n // Dual color ranges on the \"age\" column: independent gradients for background\n // (driven by age, full 0-100 range) and text color (driven by age too, but\n // with a narrower 20-80 band so the text contrast is calibrated separately).\n {\n apply: {\n colorRange: {\n maxColor: '#f00000',\n maxValue: 100,\n midColor: '#a00000',\n midValue: 50,\n minColor: '#800000',\n minValue: 0,\n onColumn: 'age',\n },\n textColorRange: {\n maxColor: '#aaaaaa',\n maxValue: 80,\n minColor: '#ffffff',\n minValue: 20,\n onColumn: 'age',\n },\n },\n column: 'age',\n priority: 2, // Lower priority so explicit green rule overrides\n },\n // Multi-column rule: all cells styled when age > 50 AND name contains \"o\"\n {\n apply: {\n color: { value: '#fef3c7' },\n textColor: { value: '#000000' },\n },\n column: null,\n priority: 0, // Lower priority so other rules take precedence\n where: {\n and: [\n { greaterThan: [{ column: 'age' }, 50] },\n { contains: [{ column: 'name' }, 'o'] },\n ],\n },\n },\n // Bigint range: adjacent values above Number.MAX_SAFE_INTEGER retain their\n // precision. Wrapped literals are JSON-safe; BigInt(...) is programmatic.\n {\n apply: {\n colorRange: {\n maxColor: '#7c3aed',\n maxValue: BIGINT_ID_START + BigInt(tableData.length - 1),\n minColor: '#ede9fe',\n minValue: { bigint: BIGINT_ID_START.toString() },\n onColumn: 'preciseId',\n },\n textColor: { value: '#111827' },\n },\n column: 'preciseId',\n priority: 1,\n },\n // Exact bigint comparison using the JSON-safe literal form.\n {\n apply: {\n color: { value: '#4c1d95' },\n textColor: { value: '#ffffff' },\n },\n column: 'preciseId',\n priority: 2,\n where: {\n equal: [\n { column: 'preciseId' },\n { bigint: (BIGINT_ID_START + BigInt(2)).toString() },\n ],\n },\n },\n // Accessible default text color: a background is set but no textColor, so an\n // accessible text color is chosen automatically for contrast against the\n // dark background. Compare the cypherCommand cell here with the one below,\n // which uses the same background but an explicit (low-contrast) textColor.\n {\n apply: { color: { value: '#1e3a5f' } },\n column: 'cypherCommand',\n priority: 1,\n where: { equal: [{ column: 'name' }, 'Ken Kessler'] },\n },\n // Explicit textColor always wins: even a low-contrast text color is left\n // untouched -- the automatic accessible default only fills in when no\n // textColor/textColorRange resolved one.\n {\n apply: {\n color: { value: '#1e3a5f' },\n textColor: { value: '#fca5a5' },\n },\n column: 'cypherCommand',\n priority: 1,\n where: { equal: [{ column: 'name' }, 'Jonathon Graham'] },\n },\n];\n\nconst Component = () => {\n const columnHelper = createColumnHelper<BigintTestDataFormat>();\n\n const columns = [\n columnHelper.accessor('name', {\n cell: (info) => info.getValue(),\n header: () => 'Name',\n minSize: 180,\n size: 220,\n }),\n columnHelper.accessor('age', {\n cell: (info) => info.renderValue(),\n header: () => 'Age',\n minSize: 80,\n }),\n columnHelper.accessor('preciseId', {\n cell: (info) => info.getValue().toString(),\n header: () => 'Bigint ID',\n minSize: 180,\n size: 180,\n }),\n columnHelper.accessor('cypherCommand', {\n cell: (info) => info.getValue(),\n header: () => 'Cypher Command',\n minSize: 400,\n size: 400,\n }),\n ];\n\n const table = useReactTable({\n columnResizeMode: 'onChange',\n columns,\n data: tableData,\n defaultColumn: {\n maxSize: 800,\n minSize: 80,\n },\n enableSorting: true,\n getCoreRowModel: getCoreRowModel(),\n getPaginationRowModel: getPaginationRowModel(),\n getSortedRowModel: getSortedRowModel(),\n initialState: {\n pagination: {\n pageSize: 10,\n },\n },\n });\n\n return (\n <div className=\"n-w-full n-bg-light-neutral-text-weakest\">\n <DataGrid\n isResizable={false}\n tableInstance={table}\n isKeyboardNavigable={false}\n styleRules={styleRules}\n styling={{\n borderStyle: 'all-sides',\n hasHoverEffects: true,\n hasZebraStriping: false,\n }}\n />\n </div>\n );\n};\n\nexport default Component;\n"]}
@@ -19,10 +19,15 @@
19
19
  * You should have received a copy of the GNU General Public License
20
20
  * along with this program. If not, see <http://www.gnu.org/licenses/>.
21
21
  */
22
+ var __importDefault = (this && this.__importDefault) || function (mod) {
23
+ return (mod && mod.__esModule) ? mod : { "default": mod };
24
+ };
22
25
  Object.defineProperty(exports, "__esModule", { value: true });
23
26
  exports.computeDataGridRowStyles = computeDataGridRowStyles;
24
27
  exports.evaluateDataGridStyleRules = evaluateDataGridStyleRules;
28
+ const base_1 = require("@neo4j-ndl/base");
25
29
  const react_color_1 = require("@uiw/react-color");
30
+ const tinycolor2_1 = __importDefault(require("tinycolor2"));
26
31
  const style_rules_1 = require("../../_generated/style-rules");
27
32
  function getInterpolatedColor(colorRange, rowData, converters) {
28
33
  const { onColumn, minValue, minColor, maxValue, maxColor, midValue, midColor, } = colorRange;
@@ -334,6 +339,24 @@ function computeDataGridRowStyles(rules, rowData, converters) {
334
339
  style[prop] = entry.value;
335
340
  hasProp = true;
336
341
  }
342
+ // If no rule set an explicit text color for this cell, but a rule did set a
343
+ // background: pick an accessible default so the user isn't left with
344
+ // low-contrast text. An explicit `textColor`/`textColorRange` (even one
345
+ // set to a color close to the background) always wins over this default.
346
+ if (style.backgroundColor &&
347
+ !style.color &&
348
+ (0, react_color_1.validHex)(style.backgroundColor)) {
349
+ style.color = tinycolor2_1.default
350
+ .mostReadable(style.backgroundColor, [
351
+ base_1.tokens.theme.light.color.neutral.text.default,
352
+ base_1.tokens.theme.dark.color.neutral.text.default,
353
+ ],
354
+ // If none of the custom colors provided meet the required readability the function
355
+ // falls back to pure black or pure white, whichever has better contrast
356
+ { includeFallbackColors: true })
357
+ .toString();
358
+ hasProp = true;
359
+ }
337
360
  cellStyles[col] = hasProp ? style : undefined;
338
361
  }
339
362
  return { cellStyles };
@@ -1 +1 @@
1
- {"version":3,"file":"evaluate.js","sourceRoot":"","sources":["../../../../src/data-grid/style-rules/evaluate.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport { color, type RgbColor, rgbToHex, validHex } from '@uiw/react-color';\n\nimport {\n clampNumericValue,\n compareNumericValues,\n getNumericWeight,\n isBigintLiteral,\n isDatetimeLiteral,\n isLocalDatetimeLiteral,\n isTimeLiteral,\n lerpColor,\n type NumericValue,\n numericValuesEqual,\n parseDateString,\n parseLocalDateString,\n parseTimeString,\n resolveNumericLiteral,\n resolveRangeLiteral,\n} from '../../_generated/style-rules';\nimport {\n type DataGridCellStyle,\n type DataGridColorRange,\n type DataGridStyleRule,\n type DataGridStyleRuleOperand,\n type DataGridStyleRuleValueConverter,\n type DataGridStyleRuleValueConverters,\n type DataGridStyleRuleWhere,\n} from './types';\n\nfunction getInterpolatedColor(\n colorRange: DataGridColorRange,\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): string | null {\n const {\n onColumn,\n minValue,\n minColor,\n maxValue,\n maxColor,\n midValue,\n midColor,\n } = colorRange;\n\n if (!validHex(minColor) || !validHex(maxColor)) {\n return null;\n }\n\n const minRgb = color(minColor).rgb;\n const maxRgb = color(maxColor).rgb;\n const resolvedMinValue = resolveRangeLiteral(minValue);\n const resolvedMaxValue = resolveRangeLiteral(maxValue);\n if (resolvedMinValue === null || resolvedMaxValue === null) {\n return null;\n }\n const boundsOrder = compareNumericValues(resolvedMinValue, resolvedMaxValue);\n if (boundsOrder === null) {\n return null;\n }\n const actualMinValue = boundsOrder <= 0 ? resolvedMinValue : resolvedMaxValue;\n const actualMaxValue = boundsOrder <= 0 ? resolvedMaxValue : resolvedMinValue;\n\n let midRgb: RgbColor | undefined = undefined;\n const resolvedMidValue =\n midValue === undefined ? undefined : resolveRangeLiteral(midValue);\n if (resolvedMidValue === null) {\n return null;\n }\n if (midValue !== undefined && midColor !== undefined) {\n const minToMid = compareNumericValues(actualMinValue, resolvedMidValue!);\n const midToMax = compareNumericValues(resolvedMidValue!, actualMaxValue);\n const isMidInRange =\n minToMid !== null && midToMax !== null && minToMid <= 0 && midToMax <= 0;\n if (!isMidInRange || !validHex(midColor)) {\n return null;\n }\n midRgb = color(midColor).rgb;\n }\n\n const rawValue = rowData[onColumn];\n const resolved = resolveCellValue(rawValue, converters?.[onColumn]);\n let numericValue: NumericValue | null = null;\n if (typeof resolved === 'bigint') {\n numericValue = resolved;\n } else if (typeof resolved === 'number' && Number.isFinite(resolved)) {\n numericValue = resolved;\n }\n if (numericValue === null) {\n return null;\n }\n\n const clampedValue = clampNumericValue(\n numericValue,\n actualMinValue,\n actualMaxValue,\n );\n if (clampedValue === null) {\n return null;\n }\n\n let rgb: RgbColor;\n\n if (midRgb !== undefined && resolvedMidValue !== undefined) {\n const t = getNumericWeight(\n resolvedMinValue,\n resolvedMidValue,\n clampedValue,\n );\n if (t === null) {\n return null;\n }\n const isBetweenMinAndMid = t <= 1;\n if (isBetweenMinAndMid) {\n rgb = lerpColor(minRgb, midRgb, t);\n } else {\n const t2 = getNumericWeight(\n resolvedMidValue,\n resolvedMaxValue,\n clampedValue,\n );\n if (t2 === null) {\n return null;\n }\n rgb = lerpColor(midRgb, maxRgb, t2);\n }\n } else {\n const t = getNumericWeight(\n resolvedMinValue,\n resolvedMaxValue,\n clampedValue,\n );\n if (t === null) {\n return null;\n }\n rgb = lerpColor(minRgb, maxRgb, t);\n }\n\n return rgbToHex(rgb);\n}\n\n// --- Where clause evaluation ---\n\ntype Ternary = boolean | null;\ntype ResolvedStyleRuleValue = string | number | bigint | boolean | null;\n\nconst UNRESOLVED = Symbol('unresolved');\n\nfunction resolveNativeValue(\n value: unknown,\n): ResolvedStyleRuleValue | typeof UNRESOLVED {\n if (value === null) {\n return null;\n }\n if (\n typeof value === 'string' ||\n typeof value === 'boolean' ||\n typeof value === 'bigint' ||\n typeof value === 'number'\n ) {\n return value;\n }\n if (value instanceof Date) {\n const ts = value.getTime();\n return isNaN(ts) ? null : ts;\n }\n if (isDatetimeLiteral(value)) {\n return parseDateString(value.datetime);\n }\n if (isLocalDatetimeLiteral(value)) {\n return parseLocalDateString(value.localdatetime);\n }\n if (isTimeLiteral(value)) {\n return parseTimeString(value.time);\n }\n if (isBigintLiteral(value)) {\n return resolveNumericLiteral(value);\n }\n return UNRESOLVED;\n}\n\nfunction resolveCellValue(\n cellVal: unknown,\n converter?: DataGridStyleRuleValueConverter,\n): ResolvedStyleRuleValue {\n if (cellVal === undefined) {\n return null;\n }\n const native = resolveNativeValue(cellVal);\n if (native !== UNRESOLVED) {\n return native;\n }\n if (converter !== undefined) {\n const converted = converter(cellVal);\n if (converted === undefined) {\n return null;\n }\n const fromConverted = resolveNativeValue(converted);\n if (fromConverted !== UNRESOLVED) {\n return fromConverted;\n }\n }\n return null;\n}\n\nfunction resolveValue(\n value: DataGridStyleRuleOperand,\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): ResolvedStyleRuleValue {\n if (typeof value === 'object' && value !== null && 'column' in value) {\n return resolveCellValue(rowData[value.column], converters?.[value.column]);\n }\n const resolved = resolveNativeValue(value);\n return resolved === UNRESOLVED ? null : resolved;\n}\n\nfunction safeCompare(\n left: DataGridStyleRuleOperand,\n right: DataGridStyleRuleOperand,\n rowData: Record<string, unknown>,\n compareFn: (\n a: NonNullable<ResolvedStyleRuleValue>,\n b: NonNullable<ResolvedStyleRuleValue>,\n ) => boolean,\n converters?: DataGridStyleRuleValueConverters,\n): Ternary {\n const leftVal = resolveValue(left, rowData, converters);\n const rightVal = resolveValue(right, rowData, converters);\n if (leftVal === null || rightVal === null) {\n return null;\n }\n return compareFn(leftVal, rightVal);\n}\n\nfunction safeStringCompare(\n left: DataGridStyleRuleOperand,\n right: DataGridStyleRuleOperand,\n rowData: Record<string, unknown>,\n compareFn: (a: string, b: string) => boolean,\n converters?: DataGridStyleRuleValueConverters,\n): Ternary {\n const leftVal = resolveValue(left, rowData, converters);\n const rightVal = resolveValue(right, rowData, converters);\n if (\n leftVal === null ||\n rightVal === null ||\n typeof leftVal !== 'string' ||\n typeof rightVal !== 'string'\n ) {\n return null;\n }\n return compareFn(leftVal, rightVal);\n}\n\nfunction evaluateWhere(\n rowData: Record<string, unknown>,\n where?: DataGridStyleRuleWhere,\n converters?: DataGridStyleRuleValueConverters,\n): Ternary {\n if (!where) {\n return true;\n }\n\n if ('equal' in where) {\n const [left, right] = where.equal;\n const leftVal = resolveValue(left, rowData, converters);\n const rightVal = resolveValue(right, rowData, converters);\n if (leftVal === null || rightVal === null) {\n return null;\n }\n if (\n (typeof leftVal === 'number' || typeof leftVal === 'bigint') &&\n (typeof rightVal === 'number' || typeof rightVal === 'bigint')\n ) {\n return numericValuesEqual(leftVal, rightVal);\n }\n return leftVal === rightVal;\n }\n\n if ('not' in where) {\n const isMatch = evaluateWhere(rowData, where.not, converters);\n return isMatch === null ? null : !isMatch;\n }\n\n if ('lessThan' in where) {\n return safeCompare(\n where.lessThan[0],\n where.lessThan[1],\n rowData,\n (a, b) => a < b,\n converters,\n );\n }\n\n if ('lessThanOrEqual' in where) {\n return safeCompare(\n where.lessThanOrEqual[0],\n where.lessThanOrEqual[1],\n rowData,\n (a, b) => a <= b,\n converters,\n );\n }\n\n if ('greaterThan' in where) {\n return safeCompare(\n where.greaterThan[0],\n where.greaterThan[1],\n rowData,\n (a, b) => a > b,\n converters,\n );\n }\n\n if ('greaterThanOrEqual' in where) {\n return safeCompare(\n where.greaterThanOrEqual[0],\n where.greaterThanOrEqual[1],\n rowData,\n (a, b) => a >= b,\n converters,\n );\n }\n\n if ('contains' in where) {\n return safeStringCompare(\n where.contains[0],\n where.contains[1],\n rowData,\n (a, b) => a.includes(b),\n converters,\n );\n }\n\n if ('startsWith' in where) {\n return safeStringCompare(\n where.startsWith[0],\n where.startsWith[1],\n rowData,\n (a, b) => a.startsWith(b),\n converters,\n );\n }\n\n if ('endsWith' in where) {\n return safeStringCompare(\n where.endsWith[0],\n where.endsWith[1],\n rowData,\n (a, b) => a.endsWith(b),\n converters,\n );\n }\n\n if ('isNull' in where) {\n const value = resolveValue(where.isNull, rowData, converters);\n return value === null;\n }\n\n if ('and' in where) {\n let hasNull = false;\n for (const clause of where.and) {\n const isMatch = evaluateWhere(rowData, clause, converters);\n if (isMatch === false) {\n return false;\n }\n if (isMatch === null) {\n hasNull = true;\n }\n }\n return hasNull ? null : true;\n }\n\n if ('or' in where) {\n let hasNull = false;\n for (const clause of where.or) {\n const isMatch = evaluateWhere(rowData, clause, converters);\n if (isMatch === true) {\n return true;\n }\n if (isMatch === null) {\n hasNull = true;\n }\n }\n return hasNull ? null : false;\n }\n\n return false;\n}\n\n// --- Style resolution ---\n\nfunction resolveAppliedStyle(\n apply: DataGridCellStyle,\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): React.CSSProperties | undefined {\n const result: React.CSSProperties = {};\n let hasStyle = false;\n\n if (apply.color && !apply.color.isDisabled) {\n result.backgroundColor = apply.color.value;\n hasStyle = true;\n }\n\n if (apply.textColor && !apply.textColor.isDisabled) {\n result.color = apply.textColor.value;\n hasStyle = true;\n }\n\n if (apply.colorRange && !apply.colorRange.isDisabled) {\n const interpolated = getInterpolatedColor(\n apply.colorRange,\n rowData,\n converters,\n );\n if (interpolated !== null) {\n result.backgroundColor = interpolated;\n hasStyle = true;\n }\n }\n\n if (apply.textColorRange && !apply.textColorRange.isDisabled) {\n const interpolated = getInterpolatedColor(\n apply.textColorRange,\n rowData,\n converters,\n );\n if (interpolated !== null) {\n result.color = interpolated;\n hasStyle = true;\n }\n }\n\n return hasStyle ? result : undefined;\n}\n\nexport type ComputedDataGridStyles = {\n cellStyles: Record<string, React.CSSProperties | undefined>;\n};\n\ntype PriorityEntry = { value: string; priority: number };\ntype PropPriorityMap = Record<string, PriorityEntry>;\n\n/**\n * Computes styles for all cells in a row based on the given style rules.\n * When a rule's `column` is `null`, its style is applied to every cell.\n *\n * Used internally by hooks, but exported for context-free usage.\n */\nexport function computeDataGridRowStyles(\n rules: DataGridStyleRule[],\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): ComputedDataGridStyles {\n const enabledRules = rules.filter((r) => !r.isDisabled);\n const totalRules = enabledRules.length;\n\n const sortedRules = enabledRules\n .map((rule, index) => {\n if (rule.priority !== undefined && rule.priority < 0) {\n throw new Error(\n `DataGridStyleRule priority must be >= 0, got ${rule.priority}. Negative values are reserved for internal use.`,\n );\n }\n\n return {\n ...rule,\n _order: index,\n _priority: rule.priority ?? index - totalRules,\n };\n })\n .sort((a, b) => {\n if (a._priority !== b._priority) {\n return a._priority - b._priority;\n }\n return a._order - b._order;\n });\n\n const cellPriorityMap: Record<string, PropPriorityMap> = {};\n\n for (const rule of sortedRules) {\n const isMatching = evaluateWhere(rowData, rule.where, converters) === true;\n if (!isMatching) {\n continue;\n }\n\n const style = resolveAppliedStyle(rule.apply, rowData, converters);\n if (!style) {\n continue;\n }\n\n const effectivePriority = rule._priority;\n const affectedColumns =\n rule.column === null ? Object.keys(rowData) : [rule.column];\n\n for (const col of affectedColumns) {\n if (!cellPriorityMap[col]) {\n cellPriorityMap[col] = {};\n }\n for (const [prop, value] of Object.entries(style)) {\n const existing = cellPriorityMap[col][prop];\n if (!existing || effectivePriority >= existing.priority) {\n cellPriorityMap[col][prop] = {\n priority: effectivePriority,\n value: value as string,\n };\n }\n }\n }\n }\n\n const cellStyles: Record<string, React.CSSProperties | undefined> = {};\n for (const [col, propMap] of Object.entries(cellPriorityMap)) {\n const style: React.CSSProperties = {};\n let hasProp = false;\n for (const [prop, entry] of Object.entries(propMap)) {\n (style as Record<string, string>)[prop] = entry.value;\n hasProp = true;\n }\n cellStyles[col] = hasProp ? style : undefined;\n }\n\n return { cellStyles };\n}\n\n/**\n * Evaluate style rules for a single cell.\n * Pure function -- no React context needed.\n *\n * @param rules - Array of style rules to evaluate\n * @param rowData - The row's data as a record (column id -> value)\n * @param columnId - Returns the computed style for this specific cell.\n * @param converters - Optional per-column value converters for complex cell types.\n */\nexport function evaluateDataGridStyleRules(\n rules: DataGridStyleRule[],\n rowData: Record<string, unknown>,\n columnId: string,\n converters?: DataGridStyleRuleValueConverters,\n): React.CSSProperties | undefined {\n const { cellStyles } = computeDataGridRowStyles(rules, rowData, converters);\n return cellStyles[columnId];\n}\n"]}
1
+ {"version":3,"file":"evaluate.js","sourceRoot":"","sources":["../../../../src/data-grid/style-rules/evaluate.ts"],"names":[],"mappings":";AAAA;;;;;;;;;;;;;;;;;;;GAmBG;;;;;AAscH,4DAmGC;AAWD,gEAQC;AA1jBD,0CAAyC;AACzC,kDAA4E;AAC5E,4DAAmC;AAEnC,8DAgBsC;AAWtC,SAAS,oBAAoB,CAC3B,UAA8B,EAC9B,OAAgC,EAChC,UAA6C;IAE7C,MAAM,EACJ,QAAQ,EACR,QAAQ,EACR,QAAQ,EACR,QAAQ,EACR,QAAQ,EACR,QAAQ,EACR,QAAQ,GACT,GAAG,UAAU,CAAC;IAEf,IAAI,CAAC,IAAA,sBAAQ,EAAC,QAAQ,CAAC,IAAI,CAAC,IAAA,sBAAQ,EAAC,QAAQ,CAAC,EAAE,CAAC;QAC/C,OAAO,IAAI,CAAC;IACd,CAAC;IAED,MAAM,MAAM,GAAG,IAAA,mBAAK,EAAC,QAAQ,CAAC,CAAC,GAAG,CAAC;IACnC,MAAM,MAAM,GAAG,IAAA,mBAAK,EAAC,QAAQ,CAAC,CAAC,GAAG,CAAC;IACnC,MAAM,gBAAgB,GAAG,IAAA,iCAAmB,EAAC,QAAQ,CAAC,CAAC;IACvD,MAAM,gBAAgB,GAAG,IAAA,iCAAmB,EAAC,QAAQ,CAAC,CAAC;IACvD,IAAI,gBAAgB,KAAK,IAAI,IAAI,gBAAgB,KAAK,IAAI,EAAE,CAAC;QAC3D,OAAO,IAAI,CAAC;IACd,CAAC;IACD,MAAM,WAAW,GAAG,IAAA,kCAAoB,EAAC,gBAAgB,EAAE,gBAAgB,CAAC,CAAC;IAC7E,IAAI,WAAW,KAAK,IAAI,EAAE,CAAC;QACzB,OAAO,IAAI,CAAC;IACd,CAAC;IACD,MAAM,cAAc,GAAG,WAAW,IAAI,CAAC,CAAC,CAAC,CAAC,gBAAgB,CAAC,CAAC,CAAC,gBAAgB,CAAC;IAC9E,MAAM,cAAc,GAAG,WAAW,IAAI,CAAC,CAAC,CAAC,CAAC,gBAAgB,CAAC,CAAC,CAAC,gBAAgB,CAAC;IAE9E,IAAI,MAAM,GAAyB,SAAS,CAAC;IAC7C,MAAM,gBAAgB,GACpB,QAAQ,KAAK,SAAS,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,IAAA,iCAAmB,EAAC,QAAQ,CAAC,CAAC;IACrE,IAAI,gBAAgB,KAAK,IAAI,EAAE,CAAC;QAC9B,OAAO,IAAI,CAAC;IACd,CAAC;IACD,IAAI,QAAQ,KAAK,SAAS,IAAI,QAAQ,KAAK,SAAS,EAAE,CAAC;QACrD,MAAM,QAAQ,GAAG,IAAA,kCAAoB,EAAC,cAAc,EAAE,gBAAiB,CAAC,CAAC;QACzE,MAAM,QAAQ,GAAG,IAAA,kCAAoB,EAAC,gBAAiB,EAAE,cAAc,CAAC,CAAC;QACzE,MAAM,YAAY,GAChB,QAAQ,KAAK,IAAI,IAAI,QAAQ,KAAK,IAAI,IAAI,QAAQ,IAAI,CAAC,IAAI,QAAQ,IAAI,CAAC,CAAC;QAC3E,IAAI,CAAC,YAAY,IAAI,CAAC,IAAA,sBAAQ,EAAC,QAAQ,CAAC,EAAE,CAAC;YACzC,OAAO,IAAI,CAAC;QACd,CAAC;QACD,MAAM,GAAG,IAAA,mBAAK,EAAC,QAAQ,CAAC,CAAC,GAAG,CAAC;IAC/B,CAAC;IAED,MAAM,QAAQ,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAC;IACnC,MAAM,QAAQ,GAAG,gBAAgB,CAAC,QAAQ,EAAE,UAAU,aAAV,UAAU,uBAAV,UAAU,CAAG,QAAQ,CAAC,CAAC,CAAC;IACpE,IAAI,YAAY,GAAwB,IAAI,CAAC;IAC7C,IAAI,OAAO,QAAQ,KAAK,QAAQ,EAAE,CAAC;QACjC,YAAY,GAAG,QAAQ,CAAC;IAC1B,CAAC;SAAM,IAAI,OAAO,QAAQ,KAAK,QAAQ,IAAI,MAAM,CAAC,QAAQ,CAAC,QAAQ,CAAC,EAAE,CAAC;QACrE,YAAY,GAAG,QAAQ,CAAC;IAC1B,CAAC;IACD,IAAI,YAAY,KAAK,IAAI,EAAE,CAAC;QAC1B,OAAO,IAAI,CAAC;IACd,CAAC;IAED,MAAM,YAAY,GAAG,IAAA,+BAAiB,EACpC,YAAY,EACZ,cAAc,EACd,cAAc,CACf,CAAC;IACF,IAAI,YAAY,KAAK,IAAI,EAAE,CAAC;QAC1B,OAAO,IAAI,CAAC;IACd,CAAC;IAED,IAAI,GAAa,CAAC;IAElB,IAAI,MAAM,KAAK,SAAS,IAAI,gBAAgB,KAAK,SAAS,EAAE,CAAC;QAC3D,MAAM,CAAC,GAAG,IAAA,8BAAgB,EACxB,gBAAgB,EAChB,gBAAgB,EAChB,YAAY,CACb,CAAC;QACF,IAAI,CAAC,KAAK,IAAI,EAAE,CAAC;YACf,OAAO,IAAI,CAAC;QACd,CAAC;QACD,MAAM,kBAAkB,GAAG,CAAC,IAAI,CAAC,CAAC;QAClC,IAAI,kBAAkB,EAAE,CAAC;YACvB,GAAG,GAAG,IAAA,uBAAS,EAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC,CAAC;QACrC,CAAC;aAAM,CAAC;YACN,MAAM,EAAE,GAAG,IAAA,8BAAgB,EACzB,gBAAgB,EAChB,gBAAgB,EAChB,YAAY,CACb,CAAC;YACF,IAAI,EAAE,KAAK,IAAI,EAAE,CAAC;gBAChB,OAAO,IAAI,CAAC;YACd,CAAC;YACD,GAAG,GAAG,IAAA,uBAAS,EAAC,MAAM,EAAE,MAAM,EAAE,EAAE,CAAC,CAAC;QACtC,CAAC;IACH,CAAC;SAAM,CAAC;QACN,MAAM,CAAC,GAAG,IAAA,8BAAgB,EACxB,gBAAgB,EAChB,gBAAgB,EAChB,YAAY,CACb,CAAC;QACF,IAAI,CAAC,KAAK,IAAI,EAAE,CAAC;YACf,OAAO,IAAI,CAAC;QACd,CAAC;QACD,GAAG,GAAG,IAAA,uBAAS,EAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC,CAAC;IACrC,CAAC;IAED,OAAO,IAAA,sBAAQ,EAAC,GAAG,CAAC,CAAC;AACvB,CAAC;AAOD,MAAM,UAAU,GAAG,MAAM,CAAC,YAAY,CAAC,CAAC;AAExC,SAAS,kBAAkB,CACzB,KAAc;IAEd,IAAI,KAAK,KAAK,IAAI,EAAE,CAAC;QACnB,OAAO,IAAI,CAAC;IACd,CAAC;IACD,IACE,OAAO,KAAK,KAAK,QAAQ;QACzB,OAAO,KAAK,KAAK,SAAS;QAC1B,OAAO,KAAK,KAAK,QAAQ;QACzB,OAAO,KAAK,KAAK,QAAQ,EACzB,CAAC;QACD,OAAO,KAAK,CAAC;IACf,CAAC;IACD,IAAI,KAAK,YAAY,IAAI,EAAE,CAAC;QAC1B,MAAM,EAAE,GAAG,KAAK,CAAC,OAAO,EAAE,CAAC;QAC3B,OAAO,KAAK,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC;IAC/B,CAAC;IACD,IAAI,IAAA,+BAAiB,EAAC,KAAK,CAAC,EAAE,CAAC;QAC7B,OAAO,IAAA,6BAAe,EAAC,KAAK,CAAC,QAAQ,CAAC,CAAC;IACzC,CAAC;IACD,IAAI,IAAA,oCAAsB,EAAC,KAAK,CAAC,EAAE,CAAC;QAClC,OAAO,IAAA,kCAAoB,EAAC,KAAK,CAAC,aAAa,CAAC,CAAC;IACnD,CAAC;IACD,IAAI,IAAA,2BAAa,EAAC,KAAK,CAAC,EAAE,CAAC;QACzB,OAAO,IAAA,6BAAe,EAAC,KAAK,CAAC,IAAI,CAAC,CAAC;IACrC,CAAC;IACD,IAAI,IAAA,6BAAe,EAAC,KAAK,CAAC,EAAE,CAAC;QAC3B,OAAO,IAAA,mCAAqB,EAAC,KAAK,CAAC,CAAC;IACtC,CAAC;IACD,OAAO,UAAU,CAAC;AACpB,CAAC;AAED,SAAS,gBAAgB,CACvB,OAAgB,EAChB,SAA2C;IAE3C,IAAI,OAAO,KAAK,SAAS,EAAE,CAAC;QAC1B,OAAO,IAAI,CAAC;IACd,CAAC;IACD,MAAM,MAAM,GAAG,kBAAkB,CAAC,OAAO,CAAC,CAAC;IAC3C,IAAI,MAAM,KAAK,UAAU,EAAE,CAAC;QAC1B,OAAO,MAAM,CAAC;IAChB,CAAC;IACD,IAAI,SAAS,KAAK,SAAS,EAAE,CAAC;QAC5B,MAAM,SAAS,GAAG,SAAS,CAAC,OAAO,CAAC,CAAC;QACrC,IAAI,SAAS,KAAK,SAAS,EAAE,CAAC;YAC5B,OAAO,IAAI,CAAC;QACd,CAAC;QACD,MAAM,aAAa,GAAG,kBAAkB,CAAC,SAAS,CAAC,CAAC;QACpD,IAAI,aAAa,KAAK,UAAU,EAAE,CAAC;YACjC,OAAO,aAAa,CAAC;QACvB,CAAC;IACH,CAAC;IACD,OAAO,IAAI,CAAC;AACd,CAAC;AAED,SAAS,YAAY,CACnB,KAA+B,EAC/B,OAAgC,EAChC,UAA6C;IAE7C,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,IAAI,QAAQ,IAAI,KAAK,EAAE,CAAC;QACrE,OAAO,gBAAgB,CAAC,OAAO,CAAC,KAAK,CAAC,MAAM,CAAC,EAAE,UAAU,aAAV,UAAU,uBAAV,UAAU,CAAG,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC;IAC7E,CAAC;IACD,MAAM,QAAQ,GAAG,kBAAkB,CAAC,KAAK,CAAC,CAAC;IAC3C,OAAO,QAAQ,KAAK,UAAU,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,QAAQ,CAAC;AACnD,CAAC;AAED,SAAS,WAAW,CAClB,IAA8B,EAC9B,KAA+B,EAC/B,OAAgC,EAChC,SAGY,EACZ,UAA6C;IAE7C,MAAM,OAAO,GAAG,YAAY,CAAC,IAAI,EAAE,OAAO,EAAE,UAAU,CAAC,CAAC;IACxD,MAAM,QAAQ,GAAG,YAAY,CAAC,KAAK,EAAE,OAAO,EAAE,UAAU,CAAC,CAAC;IAC1D,IAAI,OAAO,KAAK,IAAI,IAAI,QAAQ,KAAK,IAAI,EAAE,CAAC;QAC1C,OAAO,IAAI,CAAC;IACd,CAAC;IACD,OAAO,SAAS,CAAC,OAAO,EAAE,QAAQ,CAAC,CAAC;AACtC,CAAC;AAED,SAAS,iBAAiB,CACxB,IAA8B,EAC9B,KAA+B,EAC/B,OAAgC,EAChC,SAA4C,EAC5C,UAA6C;IAE7C,MAAM,OAAO,GAAG,YAAY,CAAC,IAAI,EAAE,OAAO,EAAE,UAAU,CAAC,CAAC;IACxD,MAAM,QAAQ,GAAG,YAAY,CAAC,KAAK,EAAE,OAAO,EAAE,UAAU,CAAC,CAAC;IAC1D,IACE,OAAO,KAAK,IAAI;QAChB,QAAQ,KAAK,IAAI;QACjB,OAAO,OAAO,KAAK,QAAQ;QAC3B,OAAO,QAAQ,KAAK,QAAQ,EAC5B,CAAC;QACD,OAAO,IAAI,CAAC;IACd,CAAC;IACD,OAAO,SAAS,CAAC,OAAO,EAAE,QAAQ,CAAC,CAAC;AACtC,CAAC;AAED,SAAS,aAAa,CACpB,OAAgC,EAChC,KAA8B,EAC9B,UAA6C;IAE7C,IAAI,CAAC,KAAK,EAAE,CAAC;QACX,OAAO,IAAI,CAAC;IACd,CAAC;IAED,IAAI,OAAO,IAAI,KAAK,EAAE,CAAC;QACrB,MAAM,CAAC,IAAI,EAAE,KAAK,CAAC,GAAG,KAAK,CAAC,KAAK,CAAC;QAClC,MAAM,OAAO,GAAG,YAAY,CAAC,IAAI,EAAE,OAAO,EAAE,UAAU,CAAC,CAAC;QACxD,MAAM,QAAQ,GAAG,YAAY,CAAC,KAAK,EAAE,OAAO,EAAE,UAAU,CAAC,CAAC;QAC1D,IAAI,OAAO,KAAK,IAAI,IAAI,QAAQ,KAAK,IAAI,EAAE,CAAC;YAC1C,OAAO,IAAI,CAAC;QACd,CAAC;QACD,IACE,CAAC,OAAO,OAAO,KAAK,QAAQ,IAAI,OAAO,OAAO,KAAK,QAAQ,CAAC;YAC5D,CAAC,OAAO,QAAQ,KAAK,QAAQ,IAAI,OAAO,QAAQ,KAAK,QAAQ,CAAC,EAC9D,CAAC;YACD,OAAO,IAAA,gCAAkB,EAAC,OAAO,EAAE,QAAQ,CAAC,CAAC;QAC/C,CAAC;QACD,OAAO,OAAO,KAAK,QAAQ,CAAC;IAC9B,CAAC;IAED,IAAI,KAAK,IAAI,KAAK,EAAE,CAAC;QACnB,MAAM,OAAO,GAAG,aAAa,CAAC,OAAO,EAAE,KAAK,CAAC,GAAG,EAAE,UAAU,CAAC,CAAC;QAC9D,OAAO,OAAO,KAAK,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC;IAC5C,CAAC;IAED,IAAI,UAAU,IAAI,KAAK,EAAE,CAAC;QACxB,OAAO,WAAW,CAChB,KAAK,CAAC,QAAQ,CAAC,CAAC,CAAC,EACjB,KAAK,CAAC,QAAQ,CAAC,CAAC,CAAC,EACjB,OAAO,EACP,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,GAAG,CAAC,EACf,UAAU,CACX,CAAC;IACJ,CAAC;IAED,IAAI,iBAAiB,IAAI,KAAK,EAAE,CAAC;QAC/B,OAAO,WAAW,CAChB,KAAK,CAAC,eAAe,CAAC,CAAC,CAAC,EACxB,KAAK,CAAC,eAAe,CAAC,CAAC,CAAC,EACxB,OAAO,EACP,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,IAAI,CAAC,EAChB,UAAU,CACX,CAAC;IACJ,CAAC;IAED,IAAI,aAAa,IAAI,KAAK,EAAE,CAAC;QAC3B,OAAO,WAAW,CAChB,KAAK,CAAC,WAAW,CAAC,CAAC,CAAC,EACpB,KAAK,CAAC,WAAW,CAAC,CAAC,CAAC,EACpB,OAAO,EACP,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,GAAG,CAAC,EACf,UAAU,CACX,CAAC;IACJ,CAAC;IAED,IAAI,oBAAoB,IAAI,KAAK,EAAE,CAAC;QAClC,OAAO,WAAW,CAChB,KAAK,CAAC,kBAAkB,CAAC,CAAC,CAAC,EAC3B,KAAK,CAAC,kBAAkB,CAAC,CAAC,CAAC,EAC3B,OAAO,EACP,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,IAAI,CAAC,EAChB,UAAU,CACX,CAAC;IACJ,CAAC;IAED,IAAI,UAAU,IAAI,KAAK,EAAE,CAAC;QACxB,OAAO,iBAAiB,CACtB,KAAK,CAAC,QAAQ,CAAC,CAAC,CAAC,EACjB,KAAK,CAAC,QAAQ,CAAC,CAAC,CAAC,EACjB,OAAO,EACP,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,EACvB,UAAU,CACX,CAAC;IACJ,CAAC;IAED,IAAI,YAAY,IAAI,KAAK,EAAE,CAAC;QAC1B,OAAO,iBAAiB,CACtB,KAAK,CAAC,UAAU,CAAC,CAAC,CAAC,EACnB,KAAK,CAAC,UAAU,CAAC,CAAC,CAAC,EACnB,OAAO,EACP,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,CAAC,EACzB,UAAU,CACX,CAAC;IACJ,CAAC;IAED,IAAI,UAAU,IAAI,KAAK,EAAE,CAAC;QACxB,OAAO,iBAAiB,CACtB,KAAK,CAAC,QAAQ,CAAC,CAAC,CAAC,EACjB,KAAK,CAAC,QAAQ,CAAC,CAAC,CAAC,EACjB,OAAO,EACP,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,EACvB,UAAU,CACX,CAAC;IACJ,CAAC;IAED,IAAI,QAAQ,IAAI,KAAK,EAAE,CAAC;QACtB,MAAM,KAAK,GAAG,YAAY,CAAC,KAAK,CAAC,MAAM,EAAE,OAAO,EAAE,UAAU,CAAC,CAAC;QAC9D,OAAO,KAAK,KAAK,IAAI,CAAC;IACxB,CAAC;IAED,IAAI,KAAK,IAAI,KAAK,EAAE,CAAC;QACnB,IAAI,OAAO,GAAG,KAAK,CAAC;QACpB,KAAK,MAAM,MAAM,IAAI,KAAK,CAAC,GAAG,EAAE,CAAC;YAC/B,MAAM,OAAO,GAAG,aAAa,CAAC,OAAO,EAAE,MAAM,EAAE,UAAU,CAAC,CAAC;YAC3D,IAAI,OAAO,KAAK,KAAK,EAAE,CAAC;gBACtB,OAAO,KAAK,CAAC;YACf,CAAC;YACD,IAAI,OAAO,KAAK,IAAI,EAAE,CAAC;gBACrB,OAAO,GAAG,IAAI,CAAC;YACjB,CAAC;QACH,CAAC;QACD,OAAO,OAAO,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC;IAC/B,CAAC;IAED,IAAI,IAAI,IAAI,KAAK,EAAE,CAAC;QAClB,IAAI,OAAO,GAAG,KAAK,CAAC;QACpB,KAAK,MAAM,MAAM,IAAI,KAAK,CAAC,EAAE,EAAE,CAAC;YAC9B,MAAM,OAAO,GAAG,aAAa,CAAC,OAAO,EAAE,MAAM,EAAE,UAAU,CAAC,CAAC;YAC3D,IAAI,OAAO,KAAK,IAAI,EAAE,CAAC;gBACrB,OAAO,IAAI,CAAC;YACd,CAAC;YACD,IAAI,OAAO,KAAK,IAAI,EAAE,CAAC;gBACrB,OAAO,GAAG,IAAI,CAAC;YACjB,CAAC;QACH,CAAC;QACD,OAAO,OAAO,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,CAAC;IAChC,CAAC;IAED,OAAO,KAAK,CAAC;AACf,CAAC;AAED,2BAA2B;AAE3B,SAAS,mBAAmB,CAC1B,KAAwB,EACxB,OAAgC,EAChC,UAA6C;IAE7C,MAAM,MAAM,GAAwB,EAAE,CAAC;IACvC,IAAI,QAAQ,GAAG,KAAK,CAAC;IAErB,IAAI,KAAK,CAAC,KAAK,IAAI,CAAC,KAAK,CAAC,KAAK,CAAC,UAAU,EAAE,CAAC;QAC3C,MAAM,CAAC,eAAe,GAAG,KAAK,CAAC,KAAK,CAAC,KAAK,CAAC;QAC3C,QAAQ,GAAG,IAAI,CAAC;IAClB,CAAC;IAED,IAAI,KAAK,CAAC,SAAS,IAAI,CAAC,KAAK,CAAC,SAAS,CAAC,UAAU,EAAE,CAAC;QACnD,MAAM,CAAC,KAAK,GAAG,KAAK,CAAC,SAAS,CAAC,KAAK,CAAC;QACrC,QAAQ,GAAG,IAAI,CAAC;IAClB,CAAC;IAED,IAAI,KAAK,CAAC,UAAU,IAAI,CAAC,KAAK,CAAC,UAAU,CAAC,UAAU,EAAE,CAAC;QACrD,MAAM,YAAY,GAAG,oBAAoB,CACvC,KAAK,CAAC,UAAU,EAChB,OAAO,EACP,UAAU,CACX,CAAC;QACF,IAAI,YAAY,KAAK,IAAI,EAAE,CAAC;YAC1B,MAAM,CAAC,eAAe,GAAG,YAAY,CAAC;YACtC,QAAQ,GAAG,IAAI,CAAC;QAClB,CAAC;IACH,CAAC;IAED,IAAI,KAAK,CAAC,cAAc,IAAI,CAAC,KAAK,CAAC,cAAc,CAAC,UAAU,EAAE,CAAC;QAC7D,MAAM,YAAY,GAAG,oBAAoB,CACvC,KAAK,CAAC,cAAc,EACpB,OAAO,EACP,UAAU,CACX,CAAC;QACF,IAAI,YAAY,KAAK,IAAI,EAAE,CAAC;YAC1B,MAAM,CAAC,KAAK,GAAG,YAAY,CAAC;YAC5B,QAAQ,GAAG,IAAI,CAAC;QAClB,CAAC;IACH,CAAC;IAED,OAAO,QAAQ,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,SAAS,CAAC;AACvC,CAAC;AASD;;;;;GAKG;AACH,SAAgB,wBAAwB,CACtC,KAA0B,EAC1B,OAAgC,EAChC,UAA6C;IAE7C,MAAM,YAAY,GAAG,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC;IACxD,MAAM,UAAU,GAAG,YAAY,CAAC,MAAM,CAAC;IAEvC,MAAM,WAAW,GAAG,YAAY;SAC7B,GAAG,CAAC,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE;;QACnB,IAAI,IAAI,CAAC,QAAQ,KAAK,SAAS,IAAI,IAAI,CAAC,QAAQ,GAAG,CAAC,EAAE,CAAC;YACrD,MAAM,IAAI,KAAK,CACb,gDAAgD,IAAI,CAAC,QAAQ,kDAAkD,CAChH,CAAC;QACJ,CAAC;QAED,uCACK,IAAI,KACP,MAAM,EAAE,KAAK,EACb,SAAS,EAAE,MAAA,IAAI,CAAC,QAAQ,mCAAI,KAAK,GAAG,UAAU,IAC9C;IACJ,CAAC,CAAC;SACD,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE;QACb,IAAI,CAAC,CAAC,SAAS,KAAK,CAAC,CAAC,SAAS,EAAE,CAAC;YAChC,OAAO,CAAC,CAAC,SAAS,GAAG,CAAC,CAAC,SAAS,CAAC;QACnC,CAAC;QACD,OAAO,CAAC,CAAC,MAAM,GAAG,CAAC,CAAC,MAAM,CAAC;IAC7B,CAAC,CAAC,CAAC;IAEL,MAAM,eAAe,GAAoC,EAAE,CAAC;IAE5D,KAAK,MAAM,IAAI,IAAI,WAAW,EAAE,CAAC;QAC/B,MAAM,UAAU,GAAG,aAAa,CAAC,OAAO,EAAE,IAAI,CAAC,KAAK,EAAE,UAAU,CAAC,KAAK,IAAI,CAAC;QAC3E,IAAI,CAAC,UAAU,EAAE,CAAC;YAChB,SAAS;QACX,CAAC;QAED,MAAM,KAAK,GAAG,mBAAmB,CAAC,IAAI,CAAC,KAAK,EAAE,OAAO,EAAE,UAAU,CAAC,CAAC;QACnE,IAAI,CAAC,KAAK,EAAE,CAAC;YACX,SAAS;QACX,CAAC;QAED,MAAM,iBAAiB,GAAG,IAAI,CAAC,SAAS,CAAC;QACzC,MAAM,eAAe,GACnB,IAAI,CAAC,MAAM,KAAK,IAAI,CAAC,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;QAE9D,KAAK,MAAM,GAAG,IAAI,eAAe,EAAE,CAAC;YAClC,IAAI,CAAC,eAAe,CAAC,GAAG,CAAC,EAAE,CAAC;gBAC1B,eAAe,CAAC,GAAG,CAAC,GAAG,EAAE,CAAC;YAC5B,CAAC;YACD,KAAK,MAAM,CAAC,IAAI,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC;gBAClD,MAAM,QAAQ,GAAG,eAAe,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,CAAC;gBAC5C,IAAI,CAAC,QAAQ,IAAI,iBAAiB,IAAI,QAAQ,CAAC,QAAQ,EAAE,CAAC;oBACxD,eAAe,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,GAAG;wBAC3B,QAAQ,EAAE,iBAAiB;wBAC3B,KAAK,EAAE,KAAe;qBACvB,CAAC;gBACJ,CAAC;YACH,CAAC;QACH,CAAC;IACH,CAAC;IAED,MAAM,UAAU,GAAoD,EAAE,CAAC;IACvE,KAAK,MAAM,CAAC,GAAG,EAAE,OAAO,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,eAAe,CAAC,EAAE,CAAC;QAC7D,MAAM,KAAK,GAAwB,EAAE,CAAC;QACtC,IAAI,OAAO,GAAG,KAAK,CAAC;QACpB,KAAK,MAAM,CAAC,IAAI,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,OAAO,CAAC,EAAE,CAAC;YACnD,KAAgC,CAAC,IAAI,CAAC,GAAG,KAAK,CAAC,KAAK,CAAC;YACtD,OAAO,GAAG,IAAI,CAAC;QACjB,CAAC;QAED,4EAA4E;QAC5E,qEAAqE;QACrE,wEAAwE;QACxE,yEAAyE;QACzE,IACE,KAAK,CAAC,eAAe;YACrB,CAAC,KAAK,CAAC,KAAK;YACZ,IAAA,sBAAQ,EAAC,KAAK,CAAC,eAAe,CAAC,EAC/B,CAAC;YACD,KAAK,CAAC,KAAK,GAAG,oBAAS;iBACpB,YAAY,CACX,KAAK,CAAC,eAAe,EACrB;gBACE,aAAM,CAAC,KAAK,CAAC,KAAK,CAAC,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,OAAO;gBAC7C,aAAM,CAAC,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,OAAO;aAC7C;YACD,mFAAmF;YACnF,wEAAwE;YACxE,EAAE,qBAAqB,EAAE,IAAI,EAAE,CAChC;iBACA,QAAQ,EAAE,CAAC;YACd,OAAO,GAAG,IAAI,CAAC;QACjB,CAAC;QAED,UAAU,CAAC,GAAG,CAAC,GAAG,OAAO,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,SAAS,CAAC;IAChD,CAAC;IAED,OAAO,EAAE,UAAU,EAAE,CAAC;AACxB,CAAC;AAED;;;;;;;;GAQG;AACH,SAAgB,0BAA0B,CACxC,KAA0B,EAC1B,OAAgC,EAChC,QAAgB,EAChB,UAA6C;IAE7C,MAAM,EAAE,UAAU,EAAE,GAAG,wBAAwB,CAAC,KAAK,EAAE,OAAO,EAAE,UAAU,CAAC,CAAC;IAC5E,OAAO,UAAU,CAAC,QAAQ,CAAC,CAAC;AAC9B,CAAC","sourcesContent":["/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport { tokens } from '@neo4j-ndl/base';\nimport { color, type RgbColor, rgbToHex, validHex } from '@uiw/react-color';\nimport tinycolor from 'tinycolor2';\n\nimport {\n clampNumericValue,\n compareNumericValues,\n getNumericWeight,\n isBigintLiteral,\n isDatetimeLiteral,\n isLocalDatetimeLiteral,\n isTimeLiteral,\n lerpColor,\n type NumericValue,\n numericValuesEqual,\n parseDateString,\n parseLocalDateString,\n parseTimeString,\n resolveNumericLiteral,\n resolveRangeLiteral,\n} from '../../_generated/style-rules';\nimport {\n type DataGridCellStyle,\n type DataGridColorRange,\n type DataGridStyleRule,\n type DataGridStyleRuleOperand,\n type DataGridStyleRuleValueConverter,\n type DataGridStyleRuleValueConverters,\n type DataGridStyleRuleWhere,\n} from './types';\n\nfunction getInterpolatedColor(\n colorRange: DataGridColorRange,\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): string | null {\n const {\n onColumn,\n minValue,\n minColor,\n maxValue,\n maxColor,\n midValue,\n midColor,\n } = colorRange;\n\n if (!validHex(minColor) || !validHex(maxColor)) {\n return null;\n }\n\n const minRgb = color(minColor).rgb;\n const maxRgb = color(maxColor).rgb;\n const resolvedMinValue = resolveRangeLiteral(minValue);\n const resolvedMaxValue = resolveRangeLiteral(maxValue);\n if (resolvedMinValue === null || resolvedMaxValue === null) {\n return null;\n }\n const boundsOrder = compareNumericValues(resolvedMinValue, resolvedMaxValue);\n if (boundsOrder === null) {\n return null;\n }\n const actualMinValue = boundsOrder <= 0 ? resolvedMinValue : resolvedMaxValue;\n const actualMaxValue = boundsOrder <= 0 ? resolvedMaxValue : resolvedMinValue;\n\n let midRgb: RgbColor | undefined = undefined;\n const resolvedMidValue =\n midValue === undefined ? undefined : resolveRangeLiteral(midValue);\n if (resolvedMidValue === null) {\n return null;\n }\n if (midValue !== undefined && midColor !== undefined) {\n const minToMid = compareNumericValues(actualMinValue, resolvedMidValue!);\n const midToMax = compareNumericValues(resolvedMidValue!, actualMaxValue);\n const isMidInRange =\n minToMid !== null && midToMax !== null && minToMid <= 0 && midToMax <= 0;\n if (!isMidInRange || !validHex(midColor)) {\n return null;\n }\n midRgb = color(midColor).rgb;\n }\n\n const rawValue = rowData[onColumn];\n const resolved = resolveCellValue(rawValue, converters?.[onColumn]);\n let numericValue: NumericValue | null = null;\n if (typeof resolved === 'bigint') {\n numericValue = resolved;\n } else if (typeof resolved === 'number' && Number.isFinite(resolved)) {\n numericValue = resolved;\n }\n if (numericValue === null) {\n return null;\n }\n\n const clampedValue = clampNumericValue(\n numericValue,\n actualMinValue,\n actualMaxValue,\n );\n if (clampedValue === null) {\n return null;\n }\n\n let rgb: RgbColor;\n\n if (midRgb !== undefined && resolvedMidValue !== undefined) {\n const t = getNumericWeight(\n resolvedMinValue,\n resolvedMidValue,\n clampedValue,\n );\n if (t === null) {\n return null;\n }\n const isBetweenMinAndMid = t <= 1;\n if (isBetweenMinAndMid) {\n rgb = lerpColor(minRgb, midRgb, t);\n } else {\n const t2 = getNumericWeight(\n resolvedMidValue,\n resolvedMaxValue,\n clampedValue,\n );\n if (t2 === null) {\n return null;\n }\n rgb = lerpColor(midRgb, maxRgb, t2);\n }\n } else {\n const t = getNumericWeight(\n resolvedMinValue,\n resolvedMaxValue,\n clampedValue,\n );\n if (t === null) {\n return null;\n }\n rgb = lerpColor(minRgb, maxRgb, t);\n }\n\n return rgbToHex(rgb);\n}\n\n// --- Where clause evaluation ---\n\ntype Ternary = boolean | null;\ntype ResolvedStyleRuleValue = string | number | bigint | boolean | null;\n\nconst UNRESOLVED = Symbol('unresolved');\n\nfunction resolveNativeValue(\n value: unknown,\n): ResolvedStyleRuleValue | typeof UNRESOLVED {\n if (value === null) {\n return null;\n }\n if (\n typeof value === 'string' ||\n typeof value === 'boolean' ||\n typeof value === 'bigint' ||\n typeof value === 'number'\n ) {\n return value;\n }\n if (value instanceof Date) {\n const ts = value.getTime();\n return isNaN(ts) ? null : ts;\n }\n if (isDatetimeLiteral(value)) {\n return parseDateString(value.datetime);\n }\n if (isLocalDatetimeLiteral(value)) {\n return parseLocalDateString(value.localdatetime);\n }\n if (isTimeLiteral(value)) {\n return parseTimeString(value.time);\n }\n if (isBigintLiteral(value)) {\n return resolveNumericLiteral(value);\n }\n return UNRESOLVED;\n}\n\nfunction resolveCellValue(\n cellVal: unknown,\n converter?: DataGridStyleRuleValueConverter,\n): ResolvedStyleRuleValue {\n if (cellVal === undefined) {\n return null;\n }\n const native = resolveNativeValue(cellVal);\n if (native !== UNRESOLVED) {\n return native;\n }\n if (converter !== undefined) {\n const converted = converter(cellVal);\n if (converted === undefined) {\n return null;\n }\n const fromConverted = resolveNativeValue(converted);\n if (fromConverted !== UNRESOLVED) {\n return fromConverted;\n }\n }\n return null;\n}\n\nfunction resolveValue(\n value: DataGridStyleRuleOperand,\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): ResolvedStyleRuleValue {\n if (typeof value === 'object' && value !== null && 'column' in value) {\n return resolveCellValue(rowData[value.column], converters?.[value.column]);\n }\n const resolved = resolveNativeValue(value);\n return resolved === UNRESOLVED ? null : resolved;\n}\n\nfunction safeCompare(\n left: DataGridStyleRuleOperand,\n right: DataGridStyleRuleOperand,\n rowData: Record<string, unknown>,\n compareFn: (\n a: NonNullable<ResolvedStyleRuleValue>,\n b: NonNullable<ResolvedStyleRuleValue>,\n ) => boolean,\n converters?: DataGridStyleRuleValueConverters,\n): Ternary {\n const leftVal = resolveValue(left, rowData, converters);\n const rightVal = resolveValue(right, rowData, converters);\n if (leftVal === null || rightVal === null) {\n return null;\n }\n return compareFn(leftVal, rightVal);\n}\n\nfunction safeStringCompare(\n left: DataGridStyleRuleOperand,\n right: DataGridStyleRuleOperand,\n rowData: Record<string, unknown>,\n compareFn: (a: string, b: string) => boolean,\n converters?: DataGridStyleRuleValueConverters,\n): Ternary {\n const leftVal = resolveValue(left, rowData, converters);\n const rightVal = resolveValue(right, rowData, converters);\n if (\n leftVal === null ||\n rightVal === null ||\n typeof leftVal !== 'string' ||\n typeof rightVal !== 'string'\n ) {\n return null;\n }\n return compareFn(leftVal, rightVal);\n}\n\nfunction evaluateWhere(\n rowData: Record<string, unknown>,\n where?: DataGridStyleRuleWhere,\n converters?: DataGridStyleRuleValueConverters,\n): Ternary {\n if (!where) {\n return true;\n }\n\n if ('equal' in where) {\n const [left, right] = where.equal;\n const leftVal = resolveValue(left, rowData, converters);\n const rightVal = resolveValue(right, rowData, converters);\n if (leftVal === null || rightVal === null) {\n return null;\n }\n if (\n (typeof leftVal === 'number' || typeof leftVal === 'bigint') &&\n (typeof rightVal === 'number' || typeof rightVal === 'bigint')\n ) {\n return numericValuesEqual(leftVal, rightVal);\n }\n return leftVal === rightVal;\n }\n\n if ('not' in where) {\n const isMatch = evaluateWhere(rowData, where.not, converters);\n return isMatch === null ? null : !isMatch;\n }\n\n if ('lessThan' in where) {\n return safeCompare(\n where.lessThan[0],\n where.lessThan[1],\n rowData,\n (a, b) => a < b,\n converters,\n );\n }\n\n if ('lessThanOrEqual' in where) {\n return safeCompare(\n where.lessThanOrEqual[0],\n where.lessThanOrEqual[1],\n rowData,\n (a, b) => a <= b,\n converters,\n );\n }\n\n if ('greaterThan' in where) {\n return safeCompare(\n where.greaterThan[0],\n where.greaterThan[1],\n rowData,\n (a, b) => a > b,\n converters,\n );\n }\n\n if ('greaterThanOrEqual' in where) {\n return safeCompare(\n where.greaterThanOrEqual[0],\n where.greaterThanOrEqual[1],\n rowData,\n (a, b) => a >= b,\n converters,\n );\n }\n\n if ('contains' in where) {\n return safeStringCompare(\n where.contains[0],\n where.contains[1],\n rowData,\n (a, b) => a.includes(b),\n converters,\n );\n }\n\n if ('startsWith' in where) {\n return safeStringCompare(\n where.startsWith[0],\n where.startsWith[1],\n rowData,\n (a, b) => a.startsWith(b),\n converters,\n );\n }\n\n if ('endsWith' in where) {\n return safeStringCompare(\n where.endsWith[0],\n where.endsWith[1],\n rowData,\n (a, b) => a.endsWith(b),\n converters,\n );\n }\n\n if ('isNull' in where) {\n const value = resolveValue(where.isNull, rowData, converters);\n return value === null;\n }\n\n if ('and' in where) {\n let hasNull = false;\n for (const clause of where.and) {\n const isMatch = evaluateWhere(rowData, clause, converters);\n if (isMatch === false) {\n return false;\n }\n if (isMatch === null) {\n hasNull = true;\n }\n }\n return hasNull ? null : true;\n }\n\n if ('or' in where) {\n let hasNull = false;\n for (const clause of where.or) {\n const isMatch = evaluateWhere(rowData, clause, converters);\n if (isMatch === true) {\n return true;\n }\n if (isMatch === null) {\n hasNull = true;\n }\n }\n return hasNull ? null : false;\n }\n\n return false;\n}\n\n// --- Style resolution ---\n\nfunction resolveAppliedStyle(\n apply: DataGridCellStyle,\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): React.CSSProperties | undefined {\n const result: React.CSSProperties = {};\n let hasStyle = false;\n\n if (apply.color && !apply.color.isDisabled) {\n result.backgroundColor = apply.color.value;\n hasStyle = true;\n }\n\n if (apply.textColor && !apply.textColor.isDisabled) {\n result.color = apply.textColor.value;\n hasStyle = true;\n }\n\n if (apply.colorRange && !apply.colorRange.isDisabled) {\n const interpolated = getInterpolatedColor(\n apply.colorRange,\n rowData,\n converters,\n );\n if (interpolated !== null) {\n result.backgroundColor = interpolated;\n hasStyle = true;\n }\n }\n\n if (apply.textColorRange && !apply.textColorRange.isDisabled) {\n const interpolated = getInterpolatedColor(\n apply.textColorRange,\n rowData,\n converters,\n );\n if (interpolated !== null) {\n result.color = interpolated;\n hasStyle = true;\n }\n }\n\n return hasStyle ? result : undefined;\n}\n\nexport type ComputedDataGridStyles = {\n cellStyles: Record<string, React.CSSProperties | undefined>;\n};\n\ntype PriorityEntry = { value: string; priority: number };\ntype PropPriorityMap = Record<string, PriorityEntry>;\n\n/**\n * Computes styles for all cells in a row based on the given style rules.\n * When a rule's `column` is `null`, its style is applied to every cell.\n *\n * Used internally by hooks, but exported for context-free usage.\n */\nexport function computeDataGridRowStyles(\n rules: DataGridStyleRule[],\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): ComputedDataGridStyles {\n const enabledRules = rules.filter((r) => !r.isDisabled);\n const totalRules = enabledRules.length;\n\n const sortedRules = enabledRules\n .map((rule, index) => {\n if (rule.priority !== undefined && rule.priority < 0) {\n throw new Error(\n `DataGridStyleRule priority must be >= 0, got ${rule.priority}. Negative values are reserved for internal use.`,\n );\n }\n\n return {\n ...rule,\n _order: index,\n _priority: rule.priority ?? index - totalRules,\n };\n })\n .sort((a, b) => {\n if (a._priority !== b._priority) {\n return a._priority - b._priority;\n }\n return a._order - b._order;\n });\n\n const cellPriorityMap: Record<string, PropPriorityMap> = {};\n\n for (const rule of sortedRules) {\n const isMatching = evaluateWhere(rowData, rule.where, converters) === true;\n if (!isMatching) {\n continue;\n }\n\n const style = resolveAppliedStyle(rule.apply, rowData, converters);\n if (!style) {\n continue;\n }\n\n const effectivePriority = rule._priority;\n const affectedColumns =\n rule.column === null ? Object.keys(rowData) : [rule.column];\n\n for (const col of affectedColumns) {\n if (!cellPriorityMap[col]) {\n cellPriorityMap[col] = {};\n }\n for (const [prop, value] of Object.entries(style)) {\n const existing = cellPriorityMap[col][prop];\n if (!existing || effectivePriority >= existing.priority) {\n cellPriorityMap[col][prop] = {\n priority: effectivePriority,\n value: value as string,\n };\n }\n }\n }\n }\n\n const cellStyles: Record<string, React.CSSProperties | undefined> = {};\n for (const [col, propMap] of Object.entries(cellPriorityMap)) {\n const style: React.CSSProperties = {};\n let hasProp = false;\n for (const [prop, entry] of Object.entries(propMap)) {\n (style as Record<string, string>)[prop] = entry.value;\n hasProp = true;\n }\n\n // If no rule set an explicit text color for this cell, but a rule did set a\n // background: pick an accessible default so the user isn't left with\n // low-contrast text. An explicit `textColor`/`textColorRange` (even one\n // set to a color close to the background) always wins over this default.\n if (\n style.backgroundColor &&\n !style.color &&\n validHex(style.backgroundColor)\n ) {\n style.color = tinycolor\n .mostReadable(\n style.backgroundColor,\n [\n tokens.theme.light.color.neutral.text.default,\n tokens.theme.dark.color.neutral.text.default,\n ],\n // If none of the custom colors provided meet the required readability the function\n // falls back to pure black or pure white, whichever has better contrast\n { includeFallbackColors: true },\n )\n .toString();\n hasProp = true;\n }\n\n cellStyles[col] = hasProp ? style : undefined;\n }\n\n return { cellStyles };\n}\n\n/**\n * Evaluate style rules for a single cell.\n * Pure function -- no React context needed.\n *\n * @param rules - Array of style rules to evaluate\n * @param rowData - The row's data as a record (column id -> value)\n * @param columnId - Returns the computed style for this specific cell.\n * @param converters - Optional per-column value converters for complex cell types.\n */\nexport function evaluateDataGridStyleRules(\n rules: DataGridStyleRule[],\n rowData: Record<string, unknown>,\n columnId: string,\n converters?: DataGridStyleRuleValueConverters,\n): React.CSSProperties | undefined {\n const { cellStyles } = computeDataGridRowStyles(rules, rowData, converters);\n return cellStyles[columnId];\n}\n"]}
@@ -109,7 +109,8 @@ export function parseTimeString(s) {
109
109
  * e.g. `"2024-01-01"`, `"2024-01-01T14:30:00"`, `"2024-01-01T14:30:00.500"`
110
110
  *
111
111
  * Strings with a time component that lack `Z`, an offset, or an IANA bracket are
112
- * parsed as UTC wall-clock time (same semantics as Neo4j `LocalDateTime`).
112
+ * parsed as UTC wall-clock time. (Neo4j `LocalDateTime` values should instead be
113
+ * parsed with {@link parseLocalDateString}, in the browser's local timezone.)
113
114
  */
114
115
  export function parseDateString(s) {
115
116
  // RFC 9557 / ZonedDateTime with IANA bracket notation
@@ -1 +1 @@
1
- {"version":3,"file":"date-utils.js","sourceRoot":"","sources":["../../../../src/_generated/style-rules/date-utils.ts"],"names":[],"mappings":"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","sourcesContent":["/*\n * AUTO-GENERATED FILE — DO NOT EDIT.\n * Source of truth: packages/style-rules/src/\n * Regenerate with `pnpm generate:shared` (runs automatically at build/dev/install).\n */\n\n/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport { Temporal } from 'temporal-polyfill';\n\nconst MS_PER_DAY = 86_400_000;\n\nfunction plainTimeToMs(pt: Temporal.PlainTime): number {\n return (\n pt.hour * 3_600_000 +\n pt.minute * 60_000 +\n pt.second * 1_000 +\n pt.millisecond\n );\n}\n\nfunction parseOffsetMs(offsetStr: string): number | null {\n const match = offsetStr.match(/^([+-])(\\d{2}):(\\d{2})$/);\n if (!match) {\n return null;\n }\n const sign = match[1] === '+' ? 1 : -1;\n return (\n sign *\n (parseInt(match[2], 10) * 3_600_000 + parseInt(match[3], 10) * 60_000)\n );\n}\n\n/**\n * Parses an ISO 8601 time string to UTC milliseconds since midnight\n * (0–86,399,999). Returns `null` if the string cannot be parsed.\n *\n * Three formats are accepted:\n * 1. Local time (no offset): `\"14:30:00\"`, `\"14:30:00.500\"` — treated as UTC\n * 2. UTC time with Z suffix: `\"14:30:00Z\"` — treated identically to the local form\n * 3. Offset time: `\"14:30:00+02:00\"` — the offset is applied so the result\n * is the equivalent UTC time of day. `\"12:00:00+01:00\"` resolves to\n * 39,600,000 (11:00 UTC), which is less than `\"12:00:00+00:00\"` (43,200,000).\n *\n * Values wrap around midnight: `\"00:00:00+01:00\"` → 82,800,000 (23:00 UTC).\n */\nexport function parseTimeString(s: string): number | null {\n // Reject datetime strings and anything with an IANA timezone bracket.\n // Temporal.PlainTime.from silently extracts the time portion from strings\n // containing a 'T' separator. IANA brackets are meaningless for time-only\n // values (there is no date to anchor DST to), so they are also rejected.\n if (s.includes('T') || s.includes('[')) {\n return null;\n }\n // Offset time: detect \"+HH:MM\" or \"-HH:MM\" suffix first. Temporal.PlainTime.from\n // silently strips offsets and returns the clock-face time, so we must handle\n // offset strings explicitly before falling through to the plain parse.\n const offsetMatch = s.match(/([+-]\\d{2}:\\d{2})(\\[.*\\])?$/);\n if (offsetMatch) {\n const offsetStr = offsetMatch[1];\n const timeStr = s.slice(0, s.indexOf(offsetStr));\n const offsetMs = parseOffsetMs(offsetStr);\n if (offsetMs !== null) {\n try {\n const localMs = plainTimeToMs(Temporal.PlainTime.from(timeStr));\n // Subtract the UTC offset to normalise to UTC time-of-day; wrap around midnight\n return (((localMs - offsetMs) % MS_PER_DAY) + MS_PER_DAY) % MS_PER_DAY;\n } catch {\n /* empty */\n }\n }\n return null;\n }\n\n // UTC time with Z suffix (e.g. \"14:30:00Z\") — strip Z and treat as local (UTC) time.\n // Only apply when there is no 'T' in the string; a datetime string like\n // \"2024-06-15T14:30:00Z\" must not be accepted here.\n const normalized = s.endsWith('Z') && !s.includes('T') ? s.slice(0, -1) : s;\n\n // Local time (no offset) — treated as UTC\n try {\n return plainTimeToMs(Temporal.PlainTime.from(normalized));\n } catch {\n /* empty */\n }\n\n return null;\n}\n\n/**\n * Parses an ISO 8601 or RFC 9557 date/datetime string to a Unix millisecond\n * timestamp. Returns `null` if the string cannot be parsed.\n *\n * Three formats are tried in order:\n * 1. RFC 9557 ZonedDateTime with IANA bracket notation\n * e.g. `\"2024-06-15T14:00:00[Europe/Stockholm]\"` (offset inferred from the\n * named timezone, including DST) or `\"2024-06-15T14:00:00+02:00[Europe/Stockholm]\"`\n * (offset explicit; bracket must agree with the IANA zone)\n * 2. UTC or fixed-offset Instant\n * e.g. `\"2024-01-01T00:00:00Z\"`, `\"2024-01-01T00:00:00+02:00\"`\n * 3. Plain date or datetime (no offset, `Z`, or IANA bracket), interpreted as UTC\n * e.g. `\"2024-01-01\"`, `\"2024-01-01T14:30:00\"`, `\"2024-01-01T14:30:00.500\"`\n *\n * Strings with a time component that lack `Z`, an offset, or an IANA bracket are\n * parsed as UTC wall-clock time (same semantics as Neo4j `LocalDateTime`).\n */\nexport function parseDateString(s: string): number | null {\n // RFC 9557 / ZonedDateTime with IANA bracket notation\n try {\n return Temporal.ZonedDateTime.from(s).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n // UTC or fixed-offset datetime (no IANA name)\n try {\n return Temporal.Instant.from(s).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n // Plain datetime — interpret as UTC.\n // Also covers date-only strings like \"2024-01-01\" (PlainDateTime.from parses\n // them as midnight), so a separate PlainDate path is not needed.\n try {\n return Temporal.PlainDateTime.from(s).toZonedDateTime('UTC')\n .epochMilliseconds;\n } catch {\n /* empty */\n }\n\n return null;\n}\n\n/**\n * Parses a plain (unzoned) ISO 8601 date or datetime string to a Unix\n * millisecond timestamp, interpreting the wall-clock time in the given\n * `timeZone` (defaults to the browser's local timezone via\n * `Temporal.Now.timeZoneId()`). Returns `null` if the string cannot be\n * parsed or contains any timezone qualifier.\n *\n * Only plain date/datetime strings are accepted — strings with `Z`, a\n * fixed UTC offset (`+02:00`), or an IANA bracket (`[Europe/Stockholm]`)\n * are **rejected** and return `null`. This mirrors the semantics of\n * Neo4j `LocalDateTime`, which has no associated timezone.\n *\n * Accepted formats:\n * - Plain datetime: `\"2024-01-01T14:30:00\"`, `\"2024-01-01T14:30:00.500\"`\n * - Date-only (treated as local midnight): `\"2024-01-01\"`\n *\n * The optional `timeZone` parameter overrides the browser's local timezone,\n * which is useful for deterministic testing.\n */\nexport function parseLocalDateString(\n s: string,\n timeZone?: string,\n): number | null {\n // Reject strings that carry explicit timezone information. This mirrors the\n // cascade in parseDateString but uses successful parsing as a rejection\n // signal rather than an acceptance signal:\n //\n // - ZonedDateTime.from succeeds → string has an IANA bracket → reject\n // - Instant.from succeeds → string has Z or a fixed offset → reject\n // - PlainDateTime.from succeeds → truly plain string → accept\n //\n // The polyfill's PlainDateTime.from() silently strips offsets/brackets\n // instead of throwing, so these two pre-checks are necessary to enforce\n // the plain-only constraint.\n try {\n Temporal.ZonedDateTime.from(s);\n return null;\n } catch {\n /* not a zoned datetime — continue */\n }\n\n try {\n Temporal.Instant.from(s);\n return null;\n } catch {\n /* not a UTC/offset instant — continue */\n }\n\n const tz = timeZone ?? Temporal.Now.timeZoneId();\n try {\n return Temporal.PlainDateTime.from(s).toZonedDateTime(tz).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n return null;\n}\n"]}
1
+ {"version":3,"file":"date-utils.js","sourceRoot":"","sources":["../../../../src/_generated/style-rules/date-utils.ts"],"names":[],"mappings":"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","sourcesContent":["/*\n * AUTO-GENERATED FILE — DO NOT EDIT.\n * Source of truth: packages/style-rules/src/\n * Regenerate with `pnpm generate:shared` (runs automatically at build/dev/install).\n */\n\n/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport { Temporal } from 'temporal-polyfill';\n\nconst MS_PER_DAY = 86_400_000;\n\nfunction plainTimeToMs(pt: Temporal.PlainTime): number {\n return (\n pt.hour * 3_600_000 +\n pt.minute * 60_000 +\n pt.second * 1_000 +\n pt.millisecond\n );\n}\n\nfunction parseOffsetMs(offsetStr: string): number | null {\n const match = offsetStr.match(/^([+-])(\\d{2}):(\\d{2})$/);\n if (!match) {\n return null;\n }\n const sign = match[1] === '+' ? 1 : -1;\n return (\n sign *\n (parseInt(match[2], 10) * 3_600_000 + parseInt(match[3], 10) * 60_000)\n );\n}\n\n/**\n * Parses an ISO 8601 time string to UTC milliseconds since midnight\n * (0–86,399,999). Returns `null` if the string cannot be parsed.\n *\n * Three formats are accepted:\n * 1. Local time (no offset): `\"14:30:00\"`, `\"14:30:00.500\"` — treated as UTC\n * 2. UTC time with Z suffix: `\"14:30:00Z\"` — treated identically to the local form\n * 3. Offset time: `\"14:30:00+02:00\"` — the offset is applied so the result\n * is the equivalent UTC time of day. `\"12:00:00+01:00\"` resolves to\n * 39,600,000 (11:00 UTC), which is less than `\"12:00:00+00:00\"` (43,200,000).\n *\n * Values wrap around midnight: `\"00:00:00+01:00\"` → 82,800,000 (23:00 UTC).\n */\nexport function parseTimeString(s: string): number | null {\n // Reject datetime strings and anything with an IANA timezone bracket.\n // Temporal.PlainTime.from silently extracts the time portion from strings\n // containing a 'T' separator. IANA brackets are meaningless for time-only\n // values (there is no date to anchor DST to), so they are also rejected.\n if (s.includes('T') || s.includes('[')) {\n return null;\n }\n // Offset time: detect \"+HH:MM\" or \"-HH:MM\" suffix first. Temporal.PlainTime.from\n // silently strips offsets and returns the clock-face time, so we must handle\n // offset strings explicitly before falling through to the plain parse.\n const offsetMatch = s.match(/([+-]\\d{2}:\\d{2})(\\[.*\\])?$/);\n if (offsetMatch) {\n const offsetStr = offsetMatch[1];\n const timeStr = s.slice(0, s.indexOf(offsetStr));\n const offsetMs = parseOffsetMs(offsetStr);\n if (offsetMs !== null) {\n try {\n const localMs = plainTimeToMs(Temporal.PlainTime.from(timeStr));\n // Subtract the UTC offset to normalise to UTC time-of-day; wrap around midnight\n return (((localMs - offsetMs) % MS_PER_DAY) + MS_PER_DAY) % MS_PER_DAY;\n } catch {\n /* empty */\n }\n }\n return null;\n }\n\n // UTC time with Z suffix (e.g. \"14:30:00Z\") — strip Z and treat as local (UTC) time.\n // Only apply when there is no 'T' in the string; a datetime string like\n // \"2024-06-15T14:30:00Z\" must not be accepted here.\n const normalized = s.endsWith('Z') && !s.includes('T') ? s.slice(0, -1) : s;\n\n // Local time (no offset) — treated as UTC\n try {\n return plainTimeToMs(Temporal.PlainTime.from(normalized));\n } catch {\n /* empty */\n }\n\n return null;\n}\n\n/**\n * Parses an ISO 8601 or RFC 9557 date/datetime string to a Unix millisecond\n * timestamp. Returns `null` if the string cannot be parsed.\n *\n * Three formats are tried in order:\n * 1. RFC 9557 ZonedDateTime with IANA bracket notation\n * e.g. `\"2024-06-15T14:00:00[Europe/Stockholm]\"` (offset inferred from the\n * named timezone, including DST) or `\"2024-06-15T14:00:00+02:00[Europe/Stockholm]\"`\n * (offset explicit; bracket must agree with the IANA zone)\n * 2. UTC or fixed-offset Instant\n * e.g. `\"2024-01-01T00:00:00Z\"`, `\"2024-01-01T00:00:00+02:00\"`\n * 3. Plain date or datetime (no offset, `Z`, or IANA bracket), interpreted as UTC\n * e.g. `\"2024-01-01\"`, `\"2024-01-01T14:30:00\"`, `\"2024-01-01T14:30:00.500\"`\n *\n * Strings with a time component that lack `Z`, an offset, or an IANA bracket are\n * parsed as UTC wall-clock time. (Neo4j `LocalDateTime` values should instead be\n * parsed with {@link parseLocalDateString}, in the browser's local timezone.)\n */\nexport function parseDateString(s: string): number | null {\n // RFC 9557 / ZonedDateTime with IANA bracket notation\n try {\n return Temporal.ZonedDateTime.from(s).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n // UTC or fixed-offset datetime (no IANA name)\n try {\n return Temporal.Instant.from(s).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n // Plain datetime — interpret as UTC.\n // Also covers date-only strings like \"2024-01-01\" (PlainDateTime.from parses\n // them as midnight), so a separate PlainDate path is not needed.\n try {\n return Temporal.PlainDateTime.from(s).toZonedDateTime('UTC')\n .epochMilliseconds;\n } catch {\n /* empty */\n }\n\n return null;\n}\n\n/**\n * Parses a plain (unzoned) ISO 8601 date or datetime string to a Unix\n * millisecond timestamp, interpreting the wall-clock time in the given\n * `timeZone` (defaults to the browser's local timezone via\n * `Temporal.Now.timeZoneId()`). Returns `null` if the string cannot be\n * parsed or contains any timezone qualifier.\n *\n * Only plain date/datetime strings are accepted — strings with `Z`, a\n * fixed UTC offset (`+02:00`), or an IANA bracket (`[Europe/Stockholm]`)\n * are **rejected** and return `null`. This mirrors the semantics of\n * Neo4j `LocalDateTime`, which has no associated timezone.\n *\n * Accepted formats:\n * - Plain datetime: `\"2024-01-01T14:30:00\"`, `\"2024-01-01T14:30:00.500\"`\n * - Date-only (treated as local midnight): `\"2024-01-01\"`\n *\n * The optional `timeZone` parameter overrides the browser's local timezone,\n * which is useful for deterministic testing.\n */\nexport function parseLocalDateString(\n s: string,\n timeZone?: string,\n): number | null {\n // Reject strings that carry explicit timezone information. This mirrors the\n // cascade in parseDateString but uses successful parsing as a rejection\n // signal rather than an acceptance signal:\n //\n // - ZonedDateTime.from succeeds → string has an IANA bracket → reject\n // - Instant.from succeeds → string has Z or a fixed offset → reject\n // - PlainDateTime.from succeeds → truly plain string → accept\n //\n // The polyfill's PlainDateTime.from() silently strips offsets/brackets\n // instead of throwing, so these two pre-checks are necessary to enforce\n // the plain-only constraint.\n try {\n Temporal.ZonedDateTime.from(s);\n return null;\n } catch {\n /* not a zoned datetime — continue */\n }\n\n try {\n Temporal.Instant.from(s);\n return null;\n } catch {\n /* not a UTC/offset instant — continue */\n }\n\n const tz = timeZone ?? Temporal.Now.timeZoneId();\n try {\n return Temporal.PlainDateTime.from(s).toZonedDateTime(tz).epochMilliseconds;\n } catch {\n /* empty */\n }\n\n return null;\n}\n"]}
@@ -114,6 +114,28 @@ const styleRules = [
114
114
  ],
115
115
  },
116
116
  },
117
+ // Accessible default text color: a background is set but no textColor, so an
118
+ // accessible text color is chosen automatically for contrast against the
119
+ // dark background. Compare the cypherCommand cell here with the one below,
120
+ // which uses the same background but an explicit (low-contrast) textColor.
121
+ {
122
+ apply: { color: { value: '#1e3a5f' } },
123
+ column: 'cypherCommand',
124
+ priority: 1,
125
+ where: { equal: [{ column: 'name' }, 'Ken Kessler'] },
126
+ },
127
+ // Explicit textColor always wins: even a low-contrast text color is left
128
+ // untouched -- the automatic accessible default only fills in when no
129
+ // textColor/textColorRange resolved one.
130
+ {
131
+ apply: {
132
+ color: { value: '#1e3a5f' },
133
+ textColor: { value: '#fca5a5' },
134
+ },
135
+ column: 'cypherCommand',
136
+ priority: 1,
137
+ where: { equal: [{ column: 'name' }, 'Jonathon Graham'] },
138
+ },
117
139
  ];
118
140
  const Component = () => {
119
141
  const columnHelper = createColumnHelper();
@@ -1 +1 @@
1
- {"version":3,"file":"datagrid-rule-based-styling.story.js","sourceRoot":"","sources":["../../../../src/data-grid/stories/datagrid-rule-based-styling.story.tsx"],"names":[],"mappings":"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","sourcesContent":["/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport '@neo4j-ndl/base/lib/neo4j-ds-styles.css';\n\nimport { DataGrid } from '@neo4j-ndl/react';\nimport {\n createColumnHelper,\n getCoreRowModel,\n getPaginationRowModel,\n getSortedRowModel,\n useReactTable,\n} from '@tanstack/react-table';\n\nimport { type DataGridStyleRule } from '../style-rules/types';\nimport { TABLE_DEMO_DATA, type TestDataFormat } from './staticData';\n\ntype BigintTestDataFormat = TestDataFormat & { preciseId: bigint };\n\nconst BIGINT_ID_START = BigInt('9007199254740993');\nconst tableData: BigintTestDataFormat[] = TABLE_DEMO_DATA.map((row, index) => ({\n ...row,\n preciseId: BIGINT_ID_START + BigInt(index),\n}));\n\nconst styleRules: DataGridStyleRule[] = [\n // Row coloring: all cells styled when name contains \"Alicia\"\n {\n apply: {\n color: { value: '#000000' },\n textColor: { value: '#ffffff' },\n },\n column: null,\n priority: 3,\n where: { contains: [{ column: 'name' }, 'Alicia'] },\n },\n // Cell coloring: cells in the \"age\" column with value 51 get green\n {\n apply: { color: { value: '#00bb00' } },\n column: 'age',\n priority: 3,\n where: { equal: [{ column: 'age' }, 51] },\n },\n // Dual color ranges on the \"age\" column: independent gradients for background\n // (driven by age, full 0-100 range) and text color (driven by age too, but\n // with a narrower 20-80 band so the text contrast is calibrated separately).\n {\n apply: {\n colorRange: {\n maxColor: '#f00000',\n maxValue: 100,\n midColor: '#a00000',\n midValue: 50,\n minColor: '#800000',\n minValue: 0,\n onColumn: 'age',\n },\n textColorRange: {\n maxColor: '#aaaaaa',\n maxValue: 80,\n minColor: '#ffffff',\n minValue: 20,\n onColumn: 'age',\n },\n },\n column: 'age',\n priority: 2, // Lower priority so explicit green rule overrides\n },\n // Multi-column rule: all cells styled when age > 50 AND name contains \"o\"\n {\n apply: {\n color: { value: '#fef3c7' },\n textColor: { value: '#000000' },\n },\n column: null,\n priority: 0, // Lower priority so other rules take precedence\n where: {\n and: [\n { greaterThan: [{ column: 'age' }, 50] },\n { contains: [{ column: 'name' }, 'o'] },\n ],\n },\n },\n // Bigint range: adjacent values above Number.MAX_SAFE_INTEGER retain their\n // precision. Wrapped literals are JSON-safe; BigInt(...) is programmatic.\n {\n apply: {\n colorRange: {\n maxColor: '#7c3aed',\n maxValue: BIGINT_ID_START + BigInt(tableData.length - 1),\n minColor: '#ede9fe',\n minValue: { bigint: BIGINT_ID_START.toString() },\n onColumn: 'preciseId',\n },\n textColor: { value: '#111827' },\n },\n column: 'preciseId',\n priority: 1,\n },\n // Exact bigint comparison using the JSON-safe literal form.\n {\n apply: {\n color: { value: '#4c1d95' },\n textColor: { value: '#ffffff' },\n },\n column: 'preciseId',\n priority: 2,\n where: {\n equal: [\n { column: 'preciseId' },\n { bigint: (BIGINT_ID_START + BigInt(2)).toString() },\n ],\n },\n },\n];\n\nconst Component = () => {\n const columnHelper = createColumnHelper<BigintTestDataFormat>();\n\n const columns = [\n columnHelper.accessor('name', {\n cell: (info) => info.getValue(),\n header: () => 'Name',\n minSize: 180,\n size: 220,\n }),\n columnHelper.accessor('age', {\n cell: (info) => info.renderValue(),\n header: () => 'Age',\n minSize: 80,\n }),\n columnHelper.accessor('preciseId', {\n cell: (info) => info.getValue().toString(),\n header: () => 'Bigint ID',\n minSize: 180,\n size: 180,\n }),\n columnHelper.accessor('cypherCommand', {\n cell: (info) => info.getValue(),\n header: () => 'Cypher Command',\n minSize: 400,\n size: 400,\n }),\n ];\n\n const table = useReactTable({\n columnResizeMode: 'onChange',\n columns,\n data: tableData,\n defaultColumn: {\n maxSize: 800,\n minSize: 80,\n },\n enableSorting: true,\n getCoreRowModel: getCoreRowModel(),\n getPaginationRowModel: getPaginationRowModel(),\n getSortedRowModel: getSortedRowModel(),\n initialState: {\n pagination: {\n pageSize: 10,\n },\n },\n });\n\n return (\n <div className=\"n-w-full n-bg-light-neutral-text-weakest\">\n <DataGrid\n isResizable={false}\n tableInstance={table}\n isKeyboardNavigable={false}\n styleRules={styleRules}\n styling={{\n borderStyle: 'all-sides',\n hasHoverEffects: true,\n hasZebraStriping: false,\n }}\n />\n </div>\n );\n};\n\nexport default Component;\n"]}
1
+ {"version":3,"file":"datagrid-rule-based-styling.story.js","sourceRoot":"","sources":["../../../../src/data-grid/stories/datagrid-rule-based-styling.story.tsx"],"names":[],"mappings":"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","sourcesContent":["/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport '@neo4j-ndl/base/lib/neo4j-ds-styles.css';\n\nimport { DataGrid } from '@neo4j-ndl/react';\nimport {\n createColumnHelper,\n getCoreRowModel,\n getPaginationRowModel,\n getSortedRowModel,\n useReactTable,\n} from '@tanstack/react-table';\n\nimport { type DataGridStyleRule } from '../style-rules/types';\nimport { TABLE_DEMO_DATA, type TestDataFormat } from './staticData';\n\ntype BigintTestDataFormat = TestDataFormat & { preciseId: bigint };\n\nconst BIGINT_ID_START = BigInt('9007199254740993');\nconst tableData: BigintTestDataFormat[] = TABLE_DEMO_DATA.map((row, index) => ({\n ...row,\n preciseId: BIGINT_ID_START + BigInt(index),\n}));\n\nconst styleRules: DataGridStyleRule[] = [\n // Row coloring: all cells styled when name contains \"Alicia\"\n {\n apply: {\n color: { value: '#000000' },\n textColor: { value: '#ffffff' },\n },\n column: null,\n priority: 3,\n where: { contains: [{ column: 'name' }, 'Alicia'] },\n },\n // Cell coloring: cells in the \"age\" column with value 51 get green\n {\n apply: { color: { value: '#00bb00' } },\n column: 'age',\n priority: 3,\n where: { equal: [{ column: 'age' }, 51] },\n },\n // Dual color ranges on the \"age\" column: independent gradients for background\n // (driven by age, full 0-100 range) and text color (driven by age too, but\n // with a narrower 20-80 band so the text contrast is calibrated separately).\n {\n apply: {\n colorRange: {\n maxColor: '#f00000',\n maxValue: 100,\n midColor: '#a00000',\n midValue: 50,\n minColor: '#800000',\n minValue: 0,\n onColumn: 'age',\n },\n textColorRange: {\n maxColor: '#aaaaaa',\n maxValue: 80,\n minColor: '#ffffff',\n minValue: 20,\n onColumn: 'age',\n },\n },\n column: 'age',\n priority: 2, // Lower priority so explicit green rule overrides\n },\n // Multi-column rule: all cells styled when age > 50 AND name contains \"o\"\n {\n apply: {\n color: { value: '#fef3c7' },\n textColor: { value: '#000000' },\n },\n column: null,\n priority: 0, // Lower priority so other rules take precedence\n where: {\n and: [\n { greaterThan: [{ column: 'age' }, 50] },\n { contains: [{ column: 'name' }, 'o'] },\n ],\n },\n },\n // Bigint range: adjacent values above Number.MAX_SAFE_INTEGER retain their\n // precision. Wrapped literals are JSON-safe; BigInt(...) is programmatic.\n {\n apply: {\n colorRange: {\n maxColor: '#7c3aed',\n maxValue: BIGINT_ID_START + BigInt(tableData.length - 1),\n minColor: '#ede9fe',\n minValue: { bigint: BIGINT_ID_START.toString() },\n onColumn: 'preciseId',\n },\n textColor: { value: '#111827' },\n },\n column: 'preciseId',\n priority: 1,\n },\n // Exact bigint comparison using the JSON-safe literal form.\n {\n apply: {\n color: { value: '#4c1d95' },\n textColor: { value: '#ffffff' },\n },\n column: 'preciseId',\n priority: 2,\n where: {\n equal: [\n { column: 'preciseId' },\n { bigint: (BIGINT_ID_START + BigInt(2)).toString() },\n ],\n },\n },\n // Accessible default text color: a background is set but no textColor, so an\n // accessible text color is chosen automatically for contrast against the\n // dark background. Compare the cypherCommand cell here with the one below,\n // which uses the same background but an explicit (low-contrast) textColor.\n {\n apply: { color: { value: '#1e3a5f' } },\n column: 'cypherCommand',\n priority: 1,\n where: { equal: [{ column: 'name' }, 'Ken Kessler'] },\n },\n // Explicit textColor always wins: even a low-contrast text color is left\n // untouched -- the automatic accessible default only fills in when no\n // textColor/textColorRange resolved one.\n {\n apply: {\n color: { value: '#1e3a5f' },\n textColor: { value: '#fca5a5' },\n },\n column: 'cypherCommand',\n priority: 1,\n where: { equal: [{ column: 'name' }, 'Jonathon Graham'] },\n },\n];\n\nconst Component = () => {\n const columnHelper = createColumnHelper<BigintTestDataFormat>();\n\n const columns = [\n columnHelper.accessor('name', {\n cell: (info) => info.getValue(),\n header: () => 'Name',\n minSize: 180,\n size: 220,\n }),\n columnHelper.accessor('age', {\n cell: (info) => info.renderValue(),\n header: () => 'Age',\n minSize: 80,\n }),\n columnHelper.accessor('preciseId', {\n cell: (info) => info.getValue().toString(),\n header: () => 'Bigint ID',\n minSize: 180,\n size: 180,\n }),\n columnHelper.accessor('cypherCommand', {\n cell: (info) => info.getValue(),\n header: () => 'Cypher Command',\n minSize: 400,\n size: 400,\n }),\n ];\n\n const table = useReactTable({\n columnResizeMode: 'onChange',\n columns,\n data: tableData,\n defaultColumn: {\n maxSize: 800,\n minSize: 80,\n },\n enableSorting: true,\n getCoreRowModel: getCoreRowModel(),\n getPaginationRowModel: getPaginationRowModel(),\n getSortedRowModel: getSortedRowModel(),\n initialState: {\n pagination: {\n pageSize: 10,\n },\n },\n });\n\n return (\n <div className=\"n-w-full n-bg-light-neutral-text-weakest\">\n <DataGrid\n isResizable={false}\n tableInstance={table}\n isKeyboardNavigable={false}\n styleRules={styleRules}\n styling={{\n borderStyle: 'all-sides',\n hasHoverEffects: true,\n hasZebraStriping: false,\n }}\n />\n </div>\n );\n};\n\nexport default Component;\n"]}
@@ -18,7 +18,9 @@
18
18
  * You should have received a copy of the GNU General Public License
19
19
  * along with this program. If not, see <http://www.gnu.org/licenses/>.
20
20
  */
21
+ import { tokens } from '@neo4j-ndl/base';
21
22
  import { color, rgbToHex, validHex } from '@uiw/react-color';
23
+ import tinycolor from 'tinycolor2';
22
24
  import { clampNumericValue, compareNumericValues, getNumericWeight, isBigintLiteral, isDatetimeLiteral, isLocalDatetimeLiteral, isTimeLiteral, lerpColor, numericValuesEqual, parseDateString, parseLocalDateString, parseTimeString, resolveNumericLiteral, resolveRangeLiteral, } from '../../_generated/style-rules';
23
25
  function getInterpolatedColor(colorRange, rowData, converters) {
24
26
  const { onColumn, minValue, minColor, maxValue, maxColor, midValue, midColor, } = colorRange;
@@ -330,6 +332,24 @@ export function computeDataGridRowStyles(rules, rowData, converters) {
330
332
  style[prop] = entry.value;
331
333
  hasProp = true;
332
334
  }
335
+ // If no rule set an explicit text color for this cell, but a rule did set a
336
+ // background: pick an accessible default so the user isn't left with
337
+ // low-contrast text. An explicit `textColor`/`textColorRange` (even one
338
+ // set to a color close to the background) always wins over this default.
339
+ if (style.backgroundColor &&
340
+ !style.color &&
341
+ validHex(style.backgroundColor)) {
342
+ style.color = tinycolor
343
+ .mostReadable(style.backgroundColor, [
344
+ tokens.theme.light.color.neutral.text.default,
345
+ tokens.theme.dark.color.neutral.text.default,
346
+ ],
347
+ // If none of the custom colors provided meet the required readability the function
348
+ // falls back to pure black or pure white, whichever has better contrast
349
+ { includeFallbackColors: true })
350
+ .toString();
351
+ hasProp = true;
352
+ }
333
353
  cellStyles[col] = hasProp ? style : undefined;
334
354
  }
335
355
  return { cellStyles };
@@ -1 +1 @@
1
- {"version":3,"file":"evaluate.js","sourceRoot":"","sources":["../../../../src/data-grid/style-rules/evaluate.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport { color, type RgbColor, rgbToHex, validHex } from '@uiw/react-color';\n\nimport {\n clampNumericValue,\n compareNumericValues,\n getNumericWeight,\n isBigintLiteral,\n isDatetimeLiteral,\n isLocalDatetimeLiteral,\n isTimeLiteral,\n lerpColor,\n type NumericValue,\n numericValuesEqual,\n parseDateString,\n parseLocalDateString,\n parseTimeString,\n resolveNumericLiteral,\n resolveRangeLiteral,\n} from '../../_generated/style-rules';\nimport {\n type DataGridCellStyle,\n type DataGridColorRange,\n type DataGridStyleRule,\n type DataGridStyleRuleOperand,\n type DataGridStyleRuleValueConverter,\n type DataGridStyleRuleValueConverters,\n type DataGridStyleRuleWhere,\n} from './types';\n\nfunction getInterpolatedColor(\n colorRange: DataGridColorRange,\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): string | null {\n const {\n onColumn,\n minValue,\n minColor,\n maxValue,\n maxColor,\n midValue,\n midColor,\n } = colorRange;\n\n if (!validHex(minColor) || !validHex(maxColor)) {\n return null;\n }\n\n const minRgb = color(minColor).rgb;\n const maxRgb = color(maxColor).rgb;\n const resolvedMinValue = resolveRangeLiteral(minValue);\n const resolvedMaxValue = resolveRangeLiteral(maxValue);\n if (resolvedMinValue === null || resolvedMaxValue === null) {\n return null;\n }\n const boundsOrder = compareNumericValues(resolvedMinValue, resolvedMaxValue);\n if (boundsOrder === null) {\n return null;\n }\n const actualMinValue = boundsOrder <= 0 ? resolvedMinValue : resolvedMaxValue;\n const actualMaxValue = boundsOrder <= 0 ? resolvedMaxValue : resolvedMinValue;\n\n let midRgb: RgbColor | undefined = undefined;\n const resolvedMidValue =\n midValue === undefined ? undefined : resolveRangeLiteral(midValue);\n if (resolvedMidValue === null) {\n return null;\n }\n if (midValue !== undefined && midColor !== undefined) {\n const minToMid = compareNumericValues(actualMinValue, resolvedMidValue!);\n const midToMax = compareNumericValues(resolvedMidValue!, actualMaxValue);\n const isMidInRange =\n minToMid !== null && midToMax !== null && minToMid <= 0 && midToMax <= 0;\n if (!isMidInRange || !validHex(midColor)) {\n return null;\n }\n midRgb = color(midColor).rgb;\n }\n\n const rawValue = rowData[onColumn];\n const resolved = resolveCellValue(rawValue, converters?.[onColumn]);\n let numericValue: NumericValue | null = null;\n if (typeof resolved === 'bigint') {\n numericValue = resolved;\n } else if (typeof resolved === 'number' && Number.isFinite(resolved)) {\n numericValue = resolved;\n }\n if (numericValue === null) {\n return null;\n }\n\n const clampedValue = clampNumericValue(\n numericValue,\n actualMinValue,\n actualMaxValue,\n );\n if (clampedValue === null) {\n return null;\n }\n\n let rgb: RgbColor;\n\n if (midRgb !== undefined && resolvedMidValue !== undefined) {\n const t = getNumericWeight(\n resolvedMinValue,\n resolvedMidValue,\n clampedValue,\n );\n if (t === null) {\n return null;\n }\n const isBetweenMinAndMid = t <= 1;\n if (isBetweenMinAndMid) {\n rgb = lerpColor(minRgb, midRgb, t);\n } else {\n const t2 = getNumericWeight(\n resolvedMidValue,\n resolvedMaxValue,\n clampedValue,\n );\n if (t2 === null) {\n return null;\n }\n rgb = lerpColor(midRgb, maxRgb, t2);\n }\n } else {\n const t = getNumericWeight(\n resolvedMinValue,\n resolvedMaxValue,\n clampedValue,\n );\n if (t === null) {\n return null;\n }\n rgb = lerpColor(minRgb, maxRgb, t);\n }\n\n return rgbToHex(rgb);\n}\n\n// --- Where clause evaluation ---\n\ntype Ternary = boolean | null;\ntype ResolvedStyleRuleValue = string | number | bigint | boolean | null;\n\nconst UNRESOLVED = Symbol('unresolved');\n\nfunction resolveNativeValue(\n value: unknown,\n): ResolvedStyleRuleValue | typeof UNRESOLVED {\n if (value === null) {\n return null;\n }\n if (\n typeof value === 'string' ||\n typeof value === 'boolean' ||\n typeof value === 'bigint' ||\n typeof value === 'number'\n ) {\n return value;\n }\n if (value instanceof Date) {\n const ts = value.getTime();\n return isNaN(ts) ? null : ts;\n }\n if (isDatetimeLiteral(value)) {\n return parseDateString(value.datetime);\n }\n if (isLocalDatetimeLiteral(value)) {\n return parseLocalDateString(value.localdatetime);\n }\n if (isTimeLiteral(value)) {\n return parseTimeString(value.time);\n }\n if (isBigintLiteral(value)) {\n return resolveNumericLiteral(value);\n }\n return UNRESOLVED;\n}\n\nfunction resolveCellValue(\n cellVal: unknown,\n converter?: DataGridStyleRuleValueConverter,\n): ResolvedStyleRuleValue {\n if (cellVal === undefined) {\n return null;\n }\n const native = resolveNativeValue(cellVal);\n if (native !== UNRESOLVED) {\n return native;\n }\n if (converter !== undefined) {\n const converted = converter(cellVal);\n if (converted === undefined) {\n return null;\n }\n const fromConverted = resolveNativeValue(converted);\n if (fromConverted !== UNRESOLVED) {\n return fromConverted;\n }\n }\n return null;\n}\n\nfunction resolveValue(\n value: DataGridStyleRuleOperand,\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): ResolvedStyleRuleValue {\n if (typeof value === 'object' && value !== null && 'column' in value) {\n return resolveCellValue(rowData[value.column], converters?.[value.column]);\n }\n const resolved = resolveNativeValue(value);\n return resolved === UNRESOLVED ? null : resolved;\n}\n\nfunction safeCompare(\n left: DataGridStyleRuleOperand,\n right: DataGridStyleRuleOperand,\n rowData: Record<string, unknown>,\n compareFn: (\n a: NonNullable<ResolvedStyleRuleValue>,\n b: NonNullable<ResolvedStyleRuleValue>,\n ) => boolean,\n converters?: DataGridStyleRuleValueConverters,\n): Ternary {\n const leftVal = resolveValue(left, rowData, converters);\n const rightVal = resolveValue(right, rowData, converters);\n if (leftVal === null || rightVal === null) {\n return null;\n }\n return compareFn(leftVal, rightVal);\n}\n\nfunction safeStringCompare(\n left: DataGridStyleRuleOperand,\n right: DataGridStyleRuleOperand,\n rowData: Record<string, unknown>,\n compareFn: (a: string, b: string) => boolean,\n converters?: DataGridStyleRuleValueConverters,\n): Ternary {\n const leftVal = resolveValue(left, rowData, converters);\n const rightVal = resolveValue(right, rowData, converters);\n if (\n leftVal === null ||\n rightVal === null ||\n typeof leftVal !== 'string' ||\n typeof rightVal !== 'string'\n ) {\n return null;\n }\n return compareFn(leftVal, rightVal);\n}\n\nfunction evaluateWhere(\n rowData: Record<string, unknown>,\n where?: DataGridStyleRuleWhere,\n converters?: DataGridStyleRuleValueConverters,\n): Ternary {\n if (!where) {\n return true;\n }\n\n if ('equal' in where) {\n const [left, right] = where.equal;\n const leftVal = resolveValue(left, rowData, converters);\n const rightVal = resolveValue(right, rowData, converters);\n if (leftVal === null || rightVal === null) {\n return null;\n }\n if (\n (typeof leftVal === 'number' || typeof leftVal === 'bigint') &&\n (typeof rightVal === 'number' || typeof rightVal === 'bigint')\n ) {\n return numericValuesEqual(leftVal, rightVal);\n }\n return leftVal === rightVal;\n }\n\n if ('not' in where) {\n const isMatch = evaluateWhere(rowData, where.not, converters);\n return isMatch === null ? null : !isMatch;\n }\n\n if ('lessThan' in where) {\n return safeCompare(\n where.lessThan[0],\n where.lessThan[1],\n rowData,\n (a, b) => a < b,\n converters,\n );\n }\n\n if ('lessThanOrEqual' in where) {\n return safeCompare(\n where.lessThanOrEqual[0],\n where.lessThanOrEqual[1],\n rowData,\n (a, b) => a <= b,\n converters,\n );\n }\n\n if ('greaterThan' in where) {\n return safeCompare(\n where.greaterThan[0],\n where.greaterThan[1],\n rowData,\n (a, b) => a > b,\n converters,\n );\n }\n\n if ('greaterThanOrEqual' in where) {\n return safeCompare(\n where.greaterThanOrEqual[0],\n where.greaterThanOrEqual[1],\n rowData,\n (a, b) => a >= b,\n converters,\n );\n }\n\n if ('contains' in where) {\n return safeStringCompare(\n where.contains[0],\n where.contains[1],\n rowData,\n (a, b) => a.includes(b),\n converters,\n );\n }\n\n if ('startsWith' in where) {\n return safeStringCompare(\n where.startsWith[0],\n where.startsWith[1],\n rowData,\n (a, b) => a.startsWith(b),\n converters,\n );\n }\n\n if ('endsWith' in where) {\n return safeStringCompare(\n where.endsWith[0],\n where.endsWith[1],\n rowData,\n (a, b) => a.endsWith(b),\n converters,\n );\n }\n\n if ('isNull' in where) {\n const value = resolveValue(where.isNull, rowData, converters);\n return value === null;\n }\n\n if ('and' in where) {\n let hasNull = false;\n for (const clause of where.and) {\n const isMatch = evaluateWhere(rowData, clause, converters);\n if (isMatch === false) {\n return false;\n }\n if (isMatch === null) {\n hasNull = true;\n }\n }\n return hasNull ? null : true;\n }\n\n if ('or' in where) {\n let hasNull = false;\n for (const clause of where.or) {\n const isMatch = evaluateWhere(rowData, clause, converters);\n if (isMatch === true) {\n return true;\n }\n if (isMatch === null) {\n hasNull = true;\n }\n }\n return hasNull ? null : false;\n }\n\n return false;\n}\n\n// --- Style resolution ---\n\nfunction resolveAppliedStyle(\n apply: DataGridCellStyle,\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): React.CSSProperties | undefined {\n const result: React.CSSProperties = {};\n let hasStyle = false;\n\n if (apply.color && !apply.color.isDisabled) {\n result.backgroundColor = apply.color.value;\n hasStyle = true;\n }\n\n if (apply.textColor && !apply.textColor.isDisabled) {\n result.color = apply.textColor.value;\n hasStyle = true;\n }\n\n if (apply.colorRange && !apply.colorRange.isDisabled) {\n const interpolated = getInterpolatedColor(\n apply.colorRange,\n rowData,\n converters,\n );\n if (interpolated !== null) {\n result.backgroundColor = interpolated;\n hasStyle = true;\n }\n }\n\n if (apply.textColorRange && !apply.textColorRange.isDisabled) {\n const interpolated = getInterpolatedColor(\n apply.textColorRange,\n rowData,\n converters,\n );\n if (interpolated !== null) {\n result.color = interpolated;\n hasStyle = true;\n }\n }\n\n return hasStyle ? result : undefined;\n}\n\nexport type ComputedDataGridStyles = {\n cellStyles: Record<string, React.CSSProperties | undefined>;\n};\n\ntype PriorityEntry = { value: string; priority: number };\ntype PropPriorityMap = Record<string, PriorityEntry>;\n\n/**\n * Computes styles for all cells in a row based on the given style rules.\n * When a rule's `column` is `null`, its style is applied to every cell.\n *\n * Used internally by hooks, but exported for context-free usage.\n */\nexport function computeDataGridRowStyles(\n rules: DataGridStyleRule[],\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): ComputedDataGridStyles {\n const enabledRules = rules.filter((r) => !r.isDisabled);\n const totalRules = enabledRules.length;\n\n const sortedRules = enabledRules\n .map((rule, index) => {\n if (rule.priority !== undefined && rule.priority < 0) {\n throw new Error(\n `DataGridStyleRule priority must be >= 0, got ${rule.priority}. Negative values are reserved for internal use.`,\n );\n }\n\n return {\n ...rule,\n _order: index,\n _priority: rule.priority ?? index - totalRules,\n };\n })\n .sort((a, b) => {\n if (a._priority !== b._priority) {\n return a._priority - b._priority;\n }\n return a._order - b._order;\n });\n\n const cellPriorityMap: Record<string, PropPriorityMap> = {};\n\n for (const rule of sortedRules) {\n const isMatching = evaluateWhere(rowData, rule.where, converters) === true;\n if (!isMatching) {\n continue;\n }\n\n const style = resolveAppliedStyle(rule.apply, rowData, converters);\n if (!style) {\n continue;\n }\n\n const effectivePriority = rule._priority;\n const affectedColumns =\n rule.column === null ? Object.keys(rowData) : [rule.column];\n\n for (const col of affectedColumns) {\n if (!cellPriorityMap[col]) {\n cellPriorityMap[col] = {};\n }\n for (const [prop, value] of Object.entries(style)) {\n const existing = cellPriorityMap[col][prop];\n if (!existing || effectivePriority >= existing.priority) {\n cellPriorityMap[col][prop] = {\n priority: effectivePriority,\n value: value as string,\n };\n }\n }\n }\n }\n\n const cellStyles: Record<string, React.CSSProperties | undefined> = {};\n for (const [col, propMap] of Object.entries(cellPriorityMap)) {\n const style: React.CSSProperties = {};\n let hasProp = false;\n for (const [prop, entry] of Object.entries(propMap)) {\n (style as Record<string, string>)[prop] = entry.value;\n hasProp = true;\n }\n cellStyles[col] = hasProp ? style : undefined;\n }\n\n return { cellStyles };\n}\n\n/**\n * Evaluate style rules for a single cell.\n * Pure function -- no React context needed.\n *\n * @param rules - Array of style rules to evaluate\n * @param rowData - The row's data as a record (column id -> value)\n * @param columnId - Returns the computed style for this specific cell.\n * @param converters - Optional per-column value converters for complex cell types.\n */\nexport function evaluateDataGridStyleRules(\n rules: DataGridStyleRule[],\n rowData: Record<string, unknown>,\n columnId: string,\n converters?: DataGridStyleRuleValueConverters,\n): React.CSSProperties | undefined {\n const { cellStyles } = computeDataGridRowStyles(rules, rowData, converters);\n return cellStyles[columnId];\n}\n"]}
1
+ {"version":3,"file":"evaluate.js","sourceRoot":"","sources":["../../../../src/data-grid/style-rules/evaluate.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n *\n * Copyright (c) \"Neo4j\"\n * Neo4j Sweden AB [http://neo4j.com]\n *\n * This file is part of Neo4j.\n *\n * Neo4j is free software: you can redistribute it and/or modify\n * it under the terms of the GNU General Public License as published by\n * the Free Software Foundation, either version 3 of the License, or\n * (at your option) any later version.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program. If not, see <http://www.gnu.org/licenses/>.\n */\n\nimport { tokens } from '@neo4j-ndl/base';\nimport { color, type RgbColor, rgbToHex, validHex } from '@uiw/react-color';\nimport tinycolor from 'tinycolor2';\n\nimport {\n clampNumericValue,\n compareNumericValues,\n getNumericWeight,\n isBigintLiteral,\n isDatetimeLiteral,\n isLocalDatetimeLiteral,\n isTimeLiteral,\n lerpColor,\n type NumericValue,\n numericValuesEqual,\n parseDateString,\n parseLocalDateString,\n parseTimeString,\n resolveNumericLiteral,\n resolveRangeLiteral,\n} from '../../_generated/style-rules';\nimport {\n type DataGridCellStyle,\n type DataGridColorRange,\n type DataGridStyleRule,\n type DataGridStyleRuleOperand,\n type DataGridStyleRuleValueConverter,\n type DataGridStyleRuleValueConverters,\n type DataGridStyleRuleWhere,\n} from './types';\n\nfunction getInterpolatedColor(\n colorRange: DataGridColorRange,\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): string | null {\n const {\n onColumn,\n minValue,\n minColor,\n maxValue,\n maxColor,\n midValue,\n midColor,\n } = colorRange;\n\n if (!validHex(minColor) || !validHex(maxColor)) {\n return null;\n }\n\n const minRgb = color(minColor).rgb;\n const maxRgb = color(maxColor).rgb;\n const resolvedMinValue = resolveRangeLiteral(minValue);\n const resolvedMaxValue = resolveRangeLiteral(maxValue);\n if (resolvedMinValue === null || resolvedMaxValue === null) {\n return null;\n }\n const boundsOrder = compareNumericValues(resolvedMinValue, resolvedMaxValue);\n if (boundsOrder === null) {\n return null;\n }\n const actualMinValue = boundsOrder <= 0 ? resolvedMinValue : resolvedMaxValue;\n const actualMaxValue = boundsOrder <= 0 ? resolvedMaxValue : resolvedMinValue;\n\n let midRgb: RgbColor | undefined = undefined;\n const resolvedMidValue =\n midValue === undefined ? undefined : resolveRangeLiteral(midValue);\n if (resolvedMidValue === null) {\n return null;\n }\n if (midValue !== undefined && midColor !== undefined) {\n const minToMid = compareNumericValues(actualMinValue, resolvedMidValue!);\n const midToMax = compareNumericValues(resolvedMidValue!, actualMaxValue);\n const isMidInRange =\n minToMid !== null && midToMax !== null && minToMid <= 0 && midToMax <= 0;\n if (!isMidInRange || !validHex(midColor)) {\n return null;\n }\n midRgb = color(midColor).rgb;\n }\n\n const rawValue = rowData[onColumn];\n const resolved = resolveCellValue(rawValue, converters?.[onColumn]);\n let numericValue: NumericValue | null = null;\n if (typeof resolved === 'bigint') {\n numericValue = resolved;\n } else if (typeof resolved === 'number' && Number.isFinite(resolved)) {\n numericValue = resolved;\n }\n if (numericValue === null) {\n return null;\n }\n\n const clampedValue = clampNumericValue(\n numericValue,\n actualMinValue,\n actualMaxValue,\n );\n if (clampedValue === null) {\n return null;\n }\n\n let rgb: RgbColor;\n\n if (midRgb !== undefined && resolvedMidValue !== undefined) {\n const t = getNumericWeight(\n resolvedMinValue,\n resolvedMidValue,\n clampedValue,\n );\n if (t === null) {\n return null;\n }\n const isBetweenMinAndMid = t <= 1;\n if (isBetweenMinAndMid) {\n rgb = lerpColor(minRgb, midRgb, t);\n } else {\n const t2 = getNumericWeight(\n resolvedMidValue,\n resolvedMaxValue,\n clampedValue,\n );\n if (t2 === null) {\n return null;\n }\n rgb = lerpColor(midRgb, maxRgb, t2);\n }\n } else {\n const t = getNumericWeight(\n resolvedMinValue,\n resolvedMaxValue,\n clampedValue,\n );\n if (t === null) {\n return null;\n }\n rgb = lerpColor(minRgb, maxRgb, t);\n }\n\n return rgbToHex(rgb);\n}\n\n// --- Where clause evaluation ---\n\ntype Ternary = boolean | null;\ntype ResolvedStyleRuleValue = string | number | bigint | boolean | null;\n\nconst UNRESOLVED = Symbol('unresolved');\n\nfunction resolveNativeValue(\n value: unknown,\n): ResolvedStyleRuleValue | typeof UNRESOLVED {\n if (value === null) {\n return null;\n }\n if (\n typeof value === 'string' ||\n typeof value === 'boolean' ||\n typeof value === 'bigint' ||\n typeof value === 'number'\n ) {\n return value;\n }\n if (value instanceof Date) {\n const ts = value.getTime();\n return isNaN(ts) ? null : ts;\n }\n if (isDatetimeLiteral(value)) {\n return parseDateString(value.datetime);\n }\n if (isLocalDatetimeLiteral(value)) {\n return parseLocalDateString(value.localdatetime);\n }\n if (isTimeLiteral(value)) {\n return parseTimeString(value.time);\n }\n if (isBigintLiteral(value)) {\n return resolveNumericLiteral(value);\n }\n return UNRESOLVED;\n}\n\nfunction resolveCellValue(\n cellVal: unknown,\n converter?: DataGridStyleRuleValueConverter,\n): ResolvedStyleRuleValue {\n if (cellVal === undefined) {\n return null;\n }\n const native = resolveNativeValue(cellVal);\n if (native !== UNRESOLVED) {\n return native;\n }\n if (converter !== undefined) {\n const converted = converter(cellVal);\n if (converted === undefined) {\n return null;\n }\n const fromConverted = resolveNativeValue(converted);\n if (fromConverted !== UNRESOLVED) {\n return fromConverted;\n }\n }\n return null;\n}\n\nfunction resolveValue(\n value: DataGridStyleRuleOperand,\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): ResolvedStyleRuleValue {\n if (typeof value === 'object' && value !== null && 'column' in value) {\n return resolveCellValue(rowData[value.column], converters?.[value.column]);\n }\n const resolved = resolveNativeValue(value);\n return resolved === UNRESOLVED ? null : resolved;\n}\n\nfunction safeCompare(\n left: DataGridStyleRuleOperand,\n right: DataGridStyleRuleOperand,\n rowData: Record<string, unknown>,\n compareFn: (\n a: NonNullable<ResolvedStyleRuleValue>,\n b: NonNullable<ResolvedStyleRuleValue>,\n ) => boolean,\n converters?: DataGridStyleRuleValueConverters,\n): Ternary {\n const leftVal = resolveValue(left, rowData, converters);\n const rightVal = resolveValue(right, rowData, converters);\n if (leftVal === null || rightVal === null) {\n return null;\n }\n return compareFn(leftVal, rightVal);\n}\n\nfunction safeStringCompare(\n left: DataGridStyleRuleOperand,\n right: DataGridStyleRuleOperand,\n rowData: Record<string, unknown>,\n compareFn: (a: string, b: string) => boolean,\n converters?: DataGridStyleRuleValueConverters,\n): Ternary {\n const leftVal = resolveValue(left, rowData, converters);\n const rightVal = resolveValue(right, rowData, converters);\n if (\n leftVal === null ||\n rightVal === null ||\n typeof leftVal !== 'string' ||\n typeof rightVal !== 'string'\n ) {\n return null;\n }\n return compareFn(leftVal, rightVal);\n}\n\nfunction evaluateWhere(\n rowData: Record<string, unknown>,\n where?: DataGridStyleRuleWhere,\n converters?: DataGridStyleRuleValueConverters,\n): Ternary {\n if (!where) {\n return true;\n }\n\n if ('equal' in where) {\n const [left, right] = where.equal;\n const leftVal = resolveValue(left, rowData, converters);\n const rightVal = resolveValue(right, rowData, converters);\n if (leftVal === null || rightVal === null) {\n return null;\n }\n if (\n (typeof leftVal === 'number' || typeof leftVal === 'bigint') &&\n (typeof rightVal === 'number' || typeof rightVal === 'bigint')\n ) {\n return numericValuesEqual(leftVal, rightVal);\n }\n return leftVal === rightVal;\n }\n\n if ('not' in where) {\n const isMatch = evaluateWhere(rowData, where.not, converters);\n return isMatch === null ? null : !isMatch;\n }\n\n if ('lessThan' in where) {\n return safeCompare(\n where.lessThan[0],\n where.lessThan[1],\n rowData,\n (a, b) => a < b,\n converters,\n );\n }\n\n if ('lessThanOrEqual' in where) {\n return safeCompare(\n where.lessThanOrEqual[0],\n where.lessThanOrEqual[1],\n rowData,\n (a, b) => a <= b,\n converters,\n );\n }\n\n if ('greaterThan' in where) {\n return safeCompare(\n where.greaterThan[0],\n where.greaterThan[1],\n rowData,\n (a, b) => a > b,\n converters,\n );\n }\n\n if ('greaterThanOrEqual' in where) {\n return safeCompare(\n where.greaterThanOrEqual[0],\n where.greaterThanOrEqual[1],\n rowData,\n (a, b) => a >= b,\n converters,\n );\n }\n\n if ('contains' in where) {\n return safeStringCompare(\n where.contains[0],\n where.contains[1],\n rowData,\n (a, b) => a.includes(b),\n converters,\n );\n }\n\n if ('startsWith' in where) {\n return safeStringCompare(\n where.startsWith[0],\n where.startsWith[1],\n rowData,\n (a, b) => a.startsWith(b),\n converters,\n );\n }\n\n if ('endsWith' in where) {\n return safeStringCompare(\n where.endsWith[0],\n where.endsWith[1],\n rowData,\n (a, b) => a.endsWith(b),\n converters,\n );\n }\n\n if ('isNull' in where) {\n const value = resolveValue(where.isNull, rowData, converters);\n return value === null;\n }\n\n if ('and' in where) {\n let hasNull = false;\n for (const clause of where.and) {\n const isMatch = evaluateWhere(rowData, clause, converters);\n if (isMatch === false) {\n return false;\n }\n if (isMatch === null) {\n hasNull = true;\n }\n }\n return hasNull ? null : true;\n }\n\n if ('or' in where) {\n let hasNull = false;\n for (const clause of where.or) {\n const isMatch = evaluateWhere(rowData, clause, converters);\n if (isMatch === true) {\n return true;\n }\n if (isMatch === null) {\n hasNull = true;\n }\n }\n return hasNull ? null : false;\n }\n\n return false;\n}\n\n// --- Style resolution ---\n\nfunction resolveAppliedStyle(\n apply: DataGridCellStyle,\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): React.CSSProperties | undefined {\n const result: React.CSSProperties = {};\n let hasStyle = false;\n\n if (apply.color && !apply.color.isDisabled) {\n result.backgroundColor = apply.color.value;\n hasStyle = true;\n }\n\n if (apply.textColor && !apply.textColor.isDisabled) {\n result.color = apply.textColor.value;\n hasStyle = true;\n }\n\n if (apply.colorRange && !apply.colorRange.isDisabled) {\n const interpolated = getInterpolatedColor(\n apply.colorRange,\n rowData,\n converters,\n );\n if (interpolated !== null) {\n result.backgroundColor = interpolated;\n hasStyle = true;\n }\n }\n\n if (apply.textColorRange && !apply.textColorRange.isDisabled) {\n const interpolated = getInterpolatedColor(\n apply.textColorRange,\n rowData,\n converters,\n );\n if (interpolated !== null) {\n result.color = interpolated;\n hasStyle = true;\n }\n }\n\n return hasStyle ? result : undefined;\n}\n\nexport type ComputedDataGridStyles = {\n cellStyles: Record<string, React.CSSProperties | undefined>;\n};\n\ntype PriorityEntry = { value: string; priority: number };\ntype PropPriorityMap = Record<string, PriorityEntry>;\n\n/**\n * Computes styles for all cells in a row based on the given style rules.\n * When a rule's `column` is `null`, its style is applied to every cell.\n *\n * Used internally by hooks, but exported for context-free usage.\n */\nexport function computeDataGridRowStyles(\n rules: DataGridStyleRule[],\n rowData: Record<string, unknown>,\n converters?: DataGridStyleRuleValueConverters,\n): ComputedDataGridStyles {\n const enabledRules = rules.filter((r) => !r.isDisabled);\n const totalRules = enabledRules.length;\n\n const sortedRules = enabledRules\n .map((rule, index) => {\n if (rule.priority !== undefined && rule.priority < 0) {\n throw new Error(\n `DataGridStyleRule priority must be >= 0, got ${rule.priority}. Negative values are reserved for internal use.`,\n );\n }\n\n return {\n ...rule,\n _order: index,\n _priority: rule.priority ?? index - totalRules,\n };\n })\n .sort((a, b) => {\n if (a._priority !== b._priority) {\n return a._priority - b._priority;\n }\n return a._order - b._order;\n });\n\n const cellPriorityMap: Record<string, PropPriorityMap> = {};\n\n for (const rule of sortedRules) {\n const isMatching = evaluateWhere(rowData, rule.where, converters) === true;\n if (!isMatching) {\n continue;\n }\n\n const style = resolveAppliedStyle(rule.apply, rowData, converters);\n if (!style) {\n continue;\n }\n\n const effectivePriority = rule._priority;\n const affectedColumns =\n rule.column === null ? Object.keys(rowData) : [rule.column];\n\n for (const col of affectedColumns) {\n if (!cellPriorityMap[col]) {\n cellPriorityMap[col] = {};\n }\n for (const [prop, value] of Object.entries(style)) {\n const existing = cellPriorityMap[col][prop];\n if (!existing || effectivePriority >= existing.priority) {\n cellPriorityMap[col][prop] = {\n priority: effectivePriority,\n value: value as string,\n };\n }\n }\n }\n }\n\n const cellStyles: Record<string, React.CSSProperties | undefined> = {};\n for (const [col, propMap] of Object.entries(cellPriorityMap)) {\n const style: React.CSSProperties = {};\n let hasProp = false;\n for (const [prop, entry] of Object.entries(propMap)) {\n (style as Record<string, string>)[prop] = entry.value;\n hasProp = true;\n }\n\n // If no rule set an explicit text color for this cell, but a rule did set a\n // background: pick an accessible default so the user isn't left with\n // low-contrast text. An explicit `textColor`/`textColorRange` (even one\n // set to a color close to the background) always wins over this default.\n if (\n style.backgroundColor &&\n !style.color &&\n validHex(style.backgroundColor)\n ) {\n style.color = tinycolor\n .mostReadable(\n style.backgroundColor,\n [\n tokens.theme.light.color.neutral.text.default,\n tokens.theme.dark.color.neutral.text.default,\n ],\n // If none of the custom colors provided meet the required readability the function\n // falls back to pure black or pure white, whichever has better contrast\n { includeFallbackColors: true },\n )\n .toString();\n hasProp = true;\n }\n\n cellStyles[col] = hasProp ? style : undefined;\n }\n\n return { cellStyles };\n}\n\n/**\n * Evaluate style rules for a single cell.\n * Pure function -- no React context needed.\n *\n * @param rules - Array of style rules to evaluate\n * @param rowData - The row's data as a record (column id -> value)\n * @param columnId - Returns the computed style for this specific cell.\n * @param converters - Optional per-column value converters for complex cell types.\n */\nexport function evaluateDataGridStyleRules(\n rules: DataGridStyleRule[],\n rowData: Record<string, unknown>,\n columnId: string,\n converters?: DataGridStyleRuleValueConverters,\n): React.CSSProperties | undefined {\n const { cellStyles } = computeDataGridRowStyles(rules, rowData, converters);\n return cellStyles[columnId];\n}\n"]}
@@ -48,7 +48,8 @@ export declare function parseTimeString(s: string): number | null;
48
48
  * e.g. `"2024-01-01"`, `"2024-01-01T14:30:00"`, `"2024-01-01T14:30:00.500"`
49
49
  *
50
50
  * Strings with a time component that lack `Z`, an offset, or an IANA bracket are
51
- * parsed as UTC wall-clock time (same semantics as Neo4j `LocalDateTime`).
51
+ * parsed as UTC wall-clock time. (Neo4j `LocalDateTime` values should instead be
52
+ * parsed with {@link parseLocalDateString}, in the browser's local timezone.)
52
53
  */
53
54
  export declare function parseDateString(s: string): number | null;
54
55
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"date-utils.d.ts","sourceRoot":"","sources":["../../../../src/_generated/style-rules/date-utils.ts"],"names":[],"mappings":"AAoDA;;;;;;;;;;;;GAYG;AACH,wBAAgB,eAAe,CAAC,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAyCxD;AAED;;;;;;;;;;;;;;;;GAgBG;AACH,wBAAgB,eAAe,CAAC,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CA0BxD;AAED;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,oBAAoB,CAClC,CAAC,EAAE,MAAM,EACT,QAAQ,CAAC,EAAE,MAAM,GAChB,MAAM,GAAG,IAAI,CAkCf"}
1
+ {"version":3,"file":"date-utils.d.ts","sourceRoot":"","sources":["../../../../src/_generated/style-rules/date-utils.ts"],"names":[],"mappings":"AAoDA;;;;;;;;;;;;GAYG;AACH,wBAAgB,eAAe,CAAC,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAyCxD;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,eAAe,CAAC,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CA0BxD;AAED;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,oBAAoB,CAClC,CAAC,EAAE,MAAM,EACT,QAAQ,CAAC,EAAE,MAAM,GAChB,MAAM,GAAG,IAAI,CAkCf"}
@@ -1 +1 @@
1
- {"version":3,"file":"datagrid-rule-based-styling.story.d.ts","sourceRoot":"","sources":["../../../../src/data-grid/stories/datagrid-rule-based-styling.story.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;GAmBG;AAEH,OAAO,yCAAyC,CAAC;AAiHjD,QAAA,MAAM,SAAS,+CA+Dd,CAAC;AAEF,eAAe,SAAS,CAAC"}
1
+ {"version":3,"file":"datagrid-rule-based-styling.story.d.ts","sourceRoot":"","sources":["../../../../src/data-grid/stories/datagrid-rule-based-styling.story.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;GAmBG;AAEH,OAAO,yCAAyC,CAAC;AAuIjD,QAAA,MAAM,SAAS,+CA+Dd,CAAC;AAEF,eAAe,SAAS,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"evaluate.d.ts","sourceRoot":"","sources":["../../../../src/data-grid/style-rules/evaluate.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;GAmBG;AAqBH,OAAO,EAGL,KAAK,iBAAiB,EAGtB,KAAK,gCAAgC,EAEtC,MAAM,SAAS,CAAC;AA0ZjB,MAAM,MAAM,sBAAsB,GAAG;IACnC,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE,KAAK,CAAC,aAAa,GAAG,SAAS,CAAC,CAAC;CAC7D,CAAC;AAKF;;;;;GAKG;AACH,wBAAgB,wBAAwB,CACtC,KAAK,EAAE,iBAAiB,EAAE,EAC1B,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAChC,UAAU,CAAC,EAAE,gCAAgC,GAC5C,sBAAsB,CAsExB;AAED;;;;;;;;GAQG;AACH,wBAAgB,0BAA0B,CACxC,KAAK,EAAE,iBAAiB,EAAE,EAC1B,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAChC,QAAQ,EAAE,MAAM,EAChB,UAAU,CAAC,EAAE,gCAAgC,GAC5C,KAAK,CAAC,aAAa,GAAG,SAAS,CAGjC"}
1
+ {"version":3,"file":"evaluate.d.ts","sourceRoot":"","sources":["../../../../src/data-grid/style-rules/evaluate.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;GAmBG;AAuBH,OAAO,EAGL,KAAK,iBAAiB,EAGtB,KAAK,gCAAgC,EAEtC,MAAM,SAAS,CAAC;AA0ZjB,MAAM,MAAM,sBAAsB,GAAG;IACnC,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE,KAAK,CAAC,aAAa,GAAG,SAAS,CAAC,CAAC;CAC7D,CAAC;AAKF;;;;;GAKG;AACH,wBAAgB,wBAAwB,CACtC,KAAK,EAAE,iBAAiB,EAAE,EAC1B,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAChC,UAAU,CAAC,EAAE,gCAAgC,GAC5C,sBAAsB,CA+FxB;AAED;;;;;;;;GAQG;AACH,wBAAgB,0BAA0B,CACxC,KAAK,EAAE,iBAAiB,EAAE,EAC1B,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAChC,QAAQ,EAAE,MAAM,EAChB,UAAU,CAAC,EAAE,gCAAgC,GAC5C,KAAK,CAAC,aAAa,GAAG,SAAS,CAGjC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@neo4j-ndl/react",
3
- "version": "4.18.8",
3
+ "version": "4.18.9",
4
4
  "sideEffects": false,
5
5
  "description": "React implementation of Neo4j Design System",
6
6
  "keywords": [
@@ -378,7 +378,7 @@
378
378
  "@types/sinon": "17.0.4",
379
379
  "@types/tinycolor2": "1.4.6",
380
380
  "@vitejs/plugin-react": "5.1.4",
381
- "@vitest/coverage-v8": "^3.2.4",
381
+ "@vitest/coverage-v8": "4.1.10",
382
382
  "a11y-contrast-color": "1.1.0",
383
383
  "chromatic": "13.3.5",
384
384
  "happo": "6.2.6",
@@ -389,10 +389,10 @@
389
389
  "react-dom": "19.2.5",
390
390
  "resize-observer-polyfill": "1.5.1",
391
391
  "sinon": "21.0.3",
392
- "storybook": "10.2.19",
392
+ "storybook": "10.5.8",
393
393
  "tsx": "4.21.0",
394
394
  "typescript": "5.9.3",
395
- "vitest": "3.2.4",
395
+ "vitest": "4.1.10",
396
396
  "yargs": "18.0.0"
397
397
  },
398
398
  "peerDependencies": {