highsoft-ui 1.0.168 → 1.0.170

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CLAUDE.md CHANGED
@@ -274,6 +274,55 @@ import { ShoppingCart01, Check, XClose } from '@untitled-ui/icons-react'
274
274
  - The icon marker is `aria-hidden` and the numeral is a CSS counter, so neither is read as content — the ordinal comes from the `<ol>` itself. Don't put meaning in the icon alone: a check/cross per row needs the words to say included or not.
275
275
  - Colors are `--HS-text-*` tokens at body-text contrast and remap in dark mode. Nothing is interactive or focusable, and nothing animates, so there is no keyboard, focus or reduced-motion behaviour to account for.
276
276
 
277
+ ### Features
278
+ Icon-led feature items: an icon, then a semibold run-in title and its description in one paragraph. `Features` lays them out in a responsive grid.
279
+ ```tsx
280
+ import { PieChart02, Code02, Globe02 } from '@untitled-ui/icons-react'
281
+
282
+ <FeatureItem icon={PieChart02} title="Vast chart collection.">
283
+ Line, spline, area, column, bar, pie and more — see{' '}
284
+ <Link href="/demo">all chart types</Link>.
285
+ </FeatureItem>
286
+
287
+ // A grid of up to 3 columns (default)
288
+ <Features>
289
+ <FeatureItem icon={PieChart02} title="Vast chart collection.">…</FeatureItem>
290
+ <FeatureItem icon={Code02} title="Works with your stack.">…</FeatureItem>
291
+ <FeatureItem icon={Globe02} title="Built for any locale.">…</FeatureItem>
292
+ </Features>
293
+
294
+ // Features that are page sections: the title becomes a run-in <h3>
295
+ <FeatureItem icon={PieChart02} title="Vast chart collection." headingLevel={3}>…</FeatureItem>
296
+
297
+ // Brand icons for the whole grid; one item overrides it
298
+ <Features iconColor="brandAlt">
299
+ <FeatureItem icon={PieChart02} title="Vast chart collection.">…</FeatureItem>
300
+ <FeatureItem icon={Code02} title="Works with your stack." iconColor="successPrimary">…</FeatureItem>
301
+ </Features>
302
+
303
+ // The lighter tertiary description — on a white background-0 surface only
304
+ <Box background={0}>
305
+ <Features descriptionColor="tertiary">…</Features>
306
+ </Box>
307
+ ```
308
+ - **`icon`** (required): an `@untitled-ui/icons-react` component. Its size is fixed (20px via `Icon`); its color is `iconColor`.
309
+ - **`title`** / **`children`**: the title and the description. They run together in **one paragraph with one font and size** (`--typography-size-100` — 14px, `--typography-lineHeight-text` — 130%) and differ **only in weight and color**: title 600 (`--typography-weight-semi`) in `--HS-text-primary-default`, description 400 in `--HS-text-secondary-default` by default. The description takes inline content such as a `Link`.
310
+ - **`iconColor`:** any text color token, a `TypographyColor` (`primary` default, `secondary`, `tertiary`, `brand`, `brandAlt`, `successPrimary`, …) — the same prop and list as `List`.
311
+ - **`descriptionColor`:** `secondary` (default) | `tertiary` (lighter, **white/background-0 surfaces only** — see Accessibility).
312
+ - Both color props work on `Features` and on `FeatureItem`: set on the grid they reach every item, set on an item they override the grid for that item. Unset, an element inherits from its ancestors (primary icon, secondary description if none sets them). They travel as the inherited custom properties `--hsui-feature-icon-color` / `--hsui-feature-description-color`, not React context, so they cascade the same way in server-rendered or static (WordPress) markup.
313
+ - **`headingLevel`:** `2`–`6` renders the title as a run-in `<hN>` and the description as its own `<p>`, both `display: inline`, so the look is unchanged. Default is a `<strong>` inside a single `<p>`.
314
+ - 16px between icon and text (`--item-spacing-700`). Figma draws 18px text, a bold title and a 32px gap; that read too large, so the component steps down to 14px, semibold and 16px.
315
+ - **`Features`** — `<ul>` grid; `columns` `1`–`4` (default `3`) is the maximum. Columns drop out as the **container** narrows (each keeps ≥256px), so it collapses inside narrow parents too, not just at viewport breakpoints. 48px between rows, 32px between columns. At a 1312px container, 3 columns are 416px — the Figma item width. `FeatureItem` renders `<li>` inside `Features` and `<div>` on its own.
316
+
317
+ **Accessibility:**
318
+ - `Features` is a real `<ul>` of `<li>`s with an explicit `role="list"` (Safari/VoiceOver drops list semantics from a `list-style: none` list without it); AT announces "list, 6 items".
319
+ - The icon is `aria-hidden` — decorative; the title carries the meaning, so never rely on the glyph (or its `iconColor`) alone. Being decorative, it isn't held to WCAG 1.4.11's 3:1 for graphics, but pale tokens weaken the layout — prefer the stronger ones.
320
+ - By default the title is `<strong>` in the paragraph, so each feature reads as one sentence. Pass `headingLevel` when features are sections of the page so screen-reader users can jump between them by heading; pick the level that fits the surrounding outline.
321
+ - **Contrast:** WCAG 1.4.3 needs 4.5:1 for the 14px regular description — 14px isn't "large" text (that starts at 24px, or 18.66px bold). The default secondary description passes on every surface in both themes (6.67:1 or more). `descriptionColor="tertiary"` only gets there on `--HS-surface-ui-background-0` (4.58:1 light, 5.65:1 dark) and the dark page background (6.3:1); it fails on the light page background and background-50 (4.07:1), dark background-50 (4.25:1) and background-100 (about 3.5:1 in both themes). The component can't see its background, so tertiary is the caller's call — on white only.
322
+ - Nothing is interactive or focusable (beyond links you put in the description) and nothing animates.
323
+ - **Link text must make sense on its own.** Screen-reader users often jump through a page's links out of context (the VoiceOver rotor, NVDA's links list), where six "much more" or "read more" links are indistinguishable. Name the destination — "all chart types", not "much more". The sentence around a vague link satisfies WCAG 2.4.4 (AA), but not the links list.
324
+ - Don't pass `title` (the HTML attribute) to `Features`: it names the whole list, so AT reads it before "list, 6 items" and it shows as a tooltip over the grid.
325
+
277
326
  ### Link
278
327
  ```tsx
279
328
  <Link href="/page">Default link</Link>
@@ -1005,6 +1054,13 @@ All components use the same `iconLeft` / `iconRight` naming:
1005
1054
  - **Do** pass an icon component to `icon` for a custom bullet
1006
1055
  - **Don't** write bullets or numbers into the item text (`•`, `1.`) — the component draws them
1007
1056
 
1057
+ ### Features
1058
+ - **Do** swap the icon per feature, and color it with `iconColor` when the section calls for it
1059
+ - **Do** keep `descriptionColor="tertiary"` for white/background-0 surfaces — on the page background or any grey it fails contrast
1060
+ - **Don't** resize the icon or restyle the text through `className`/`style` — colors go through `iconColor`/`descriptionColor`; size and weight are the design
1061
+ - **Do** end the title with a full stop, as in the design, so the run-in reads as a sentence
1062
+ - **Don't** put a `Heading` or `Typography` inside `title`/`children` — title and description share the paragraph's font and size
1063
+
1008
1064
  ### Label
1009
1065
  - **Do** use `iconLeft={false}` for plain text labels like version numbers
1010
1066
  - **Don't** use Label for long text — it's designed for short status/category tags
package/LICENSE.txt ADDED
@@ -0,0 +1,11 @@
1
+ Commercial use of this software is governed by the Highsoft Standard License Agreement
2
+ found at:
3
+
4
+ https://www.highcharts.com/license
5
+
6
+ Non-commercial use of this software is governed by the Highsoft End-User License Agreement (EULA)
7
+ found at:
8
+
9
+ https://www.highcharts.com/license-eula
10
+
11
+ By installing or using this software, you agree to these terms.
package/README.md CHANGED
@@ -254,3 +254,7 @@ Not supported:
254
254
  ### Husky
255
255
 
256
256
  - Automatically lint your commit messages, code, and run tests upon committing or pushing.
257
+
258
+ ## License
259
+
260
+ Highsoft UI is **not** open source. Commercial use is governed by the [Highsoft Standard License Agreement](https://www.highcharts.com/license); non-commercial use by the [Highsoft End-User License Agreement](https://www.highcharts.com/license-eula). See [`LICENSE.txt`](./LICENSE.txt).
@@ -0,0 +1,93 @@
1
+ "use client";
2
+ import { t as e } from "./clsx-BWCAbrjV.js";
3
+ import { t } from "./Icon-DJTgdvsG.js";
4
+ import { t as n } from "./Typography-DI1AkqiO.js";
5
+ import { createContext as r, forwardRef as i, useContext as a } from "react";
6
+ import { jsx as o, jsxs as s } from "react/jsx-runtime";
7
+ var c = {
8
+ description: "T9BqNG_description",
9
+ features: "T9BqNG_features",
10
+ icon: "T9BqNG_icon",
11
+ item: "T9BqNG_item",
12
+ text: "T9BqNG_text",
13
+ title: "T9BqNG_title"
14
+ };
15
+ //#endregion
16
+ //#region lib/components/Features/index.tsx
17
+ function l({ iconColor: e, descriptionColor: t }) {
18
+ return {
19
+ ...e && { "--hsui-feature-icon-color": n[e] },
20
+ ...t && { "--hsui-feature-description-color": n[t] }
21
+ };
22
+ }
23
+ var u = r(!1), d = i(({ columns: t = 3, iconColor: n, descriptionColor: r, className: i, style: a, children: s, ...d }, f) => /* @__PURE__ */ o(u.Provider, {
24
+ value: !0,
25
+ children: /* @__PURE__ */ o("ul", {
26
+ className: e("hsui-features", i, c.features),
27
+ ref: f,
28
+ role: "list",
29
+ style: {
30
+ "--hsui-features-columns": t,
31
+ ...l({
32
+ iconColor: n,
33
+ descriptionColor: r
34
+ }),
35
+ ...a
36
+ },
37
+ ...d,
38
+ children: s
39
+ })
40
+ }));
41
+ d.displayName = "Features";
42
+ var f = i(({ icon: n, title: r, headingLevel: i, iconColor: d, descriptionColor: f, className: p, style: m, children: h, ...g }, _) => {
43
+ let v = a(u) ? "li" : "div", y = i ? `h${i}` : null;
44
+ return /* @__PURE__ */ s(v, {
45
+ className: e("hsui-feature-item", p, c.item),
46
+ ref: _,
47
+ style: {
48
+ ...l({
49
+ iconColor: d,
50
+ descriptionColor: f
51
+ }),
52
+ ...m
53
+ },
54
+ ...g,
55
+ children: [/* @__PURE__ */ o("span", {
56
+ className: c.icon,
57
+ "aria-hidden": "true",
58
+ children: /* @__PURE__ */ o(t, {
59
+ name: n,
60
+ size: 20
61
+ })
62
+ }), y ? /* @__PURE__ */ s("div", {
63
+ className: c.text,
64
+ children: [
65
+ /* @__PURE__ */ o(y, {
66
+ className: c.title,
67
+ children: r
68
+ }),
69
+ " ",
70
+ /* @__PURE__ */ o("p", {
71
+ className: c.description,
72
+ children: h
73
+ })
74
+ ]
75
+ }) : /* @__PURE__ */ s("p", {
76
+ className: c.text,
77
+ children: [
78
+ /* @__PURE__ */ o("strong", {
79
+ className: c.title,
80
+ children: r
81
+ }),
82
+ " ",
83
+ /* @__PURE__ */ o("span", {
84
+ className: c.description,
85
+ children: h
86
+ })
87
+ ]
88
+ })]
89
+ });
90
+ });
91
+ f.displayName = "FeatureItem";
92
+ //#endregion
93
+ export { d as n, f as t };
@@ -0,0 +1,2 @@
1
+ import { n as e, t } from "../../Features-BS-_cksu.js";
2
+ export { t as FeatureItem, e as Features };