@rizom/ui 0.2.0-alpha.39 → 0.2.0-alpha.41

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@rizom/ui",
3
- "version": "0.2.0-alpha.39",
3
+ "version": "0.2.0-alpha.41",
4
4
  "description": "Shared Rizom UI primitives for app-owned Rizom site variants.",
5
5
  "type": "module",
6
6
  "main": "./src/index.ts",
@@ -0,0 +1,108 @@
1
+ import type { JSX } from "preact";
2
+ import { Section } from "./Section";
3
+ import { Wordmark } from "./Wordmark";
4
+ import { renderHighlightedText } from "./highlighted-text";
5
+ import type { RizomBrandSuffix } from "./types";
6
+
7
+ const HIGHLIGHT_CLS = "italic text-accent font-normal";
8
+
9
+ export interface EcosystemCard {
10
+ suffix: RizomBrandSuffix;
11
+ title: string;
12
+ body: string;
13
+ linkLabel: string;
14
+ linkHref: string;
15
+ }
16
+
17
+ export interface EcosystemContent {
18
+ eyebrow: string;
19
+ headline: string;
20
+ cards: EcosystemCard[];
21
+ }
22
+
23
+ const HERE_LABEL = "You are here";
24
+
25
+ const ROLE_COLOR: Record<RizomBrandSuffix, string> = {
26
+ work: "text-accent",
27
+ foundation: "text-secondary",
28
+ ai: "text-accent-bright",
29
+ };
30
+
31
+ const BORDER_COLOR: Record<RizomBrandSuffix, string> = {
32
+ work: "border-t-accent/60",
33
+ foundation: "border-t-secondary/60",
34
+ ai: "border-t-accent-bright/60",
35
+ };
36
+
37
+ const HOVER_BORDER: Record<RizomBrandSuffix, string> = {
38
+ work: "hover:border-t-accent",
39
+ foundation: "hover:border-t-secondary",
40
+ ai: "hover:border-t-accent-bright",
41
+ };
42
+
43
+ const ROLE_CLS = "font-label text-[10.5px] uppercase tracking-[0.26em] mt-1";
44
+ const TAGLINE_CLS = "font-body text-[15px] leading-[1.6] text-theme-muted mt-2";
45
+ const LINK_CLS =
46
+ "font-label text-[10.5px] uppercase tracking-[0.22em] text-theme-muted self-start mt-[18px] pb-1 border-b border-white/10 transition-colors hover:text-theme";
47
+ const HERE_CLS =
48
+ "font-label text-[10.5px] uppercase tracking-[0.22em] text-accent self-start mt-[18px] pb-1";
49
+
50
+ const Card = ({ card }: { card: EcosystemCard }): JSX.Element => {
51
+ const isHere = card.linkLabel === HERE_LABEL;
52
+ const isDisabled = card.linkHref.trim().length === 0;
53
+ const inner = (
54
+ <>
55
+ <Wordmark
56
+ brandSuffix={card.suffix}
57
+ className="text-[clamp(28px,3vw,40px)] [font-variation-settings:'opsz'_96]"
58
+ />
59
+ <span className={`${ROLE_CLS} ${ROLE_COLOR[card.suffix]}`}>
60
+ {card.title}
61
+ </span>
62
+ <p className={TAGLINE_CLS}>{card.body}</p>
63
+ {isHere ? (
64
+ <span className={HERE_CLS}>{card.linkLabel}</span>
65
+ ) : (
66
+ <span className={LINK_CLS}>{card.linkLabel}</span>
67
+ )}
68
+ </>
69
+ );
70
+ const baseClass = `flex flex-col gap-[14px] border-t pt-7 ${
71
+ isHere ? BORDER_COLOR[card.suffix] : "border-white/10"
72
+ }`;
73
+ return isHere || isDisabled ? (
74
+ <div className={baseClass}>{inner}</div>
75
+ ) : (
76
+ <a
77
+ href={card.linkHref}
78
+ className={`${baseClass} text-inherit no-underline transition-colors ${HOVER_BORDER[card.suffix]}`}
79
+ >
80
+ {inner}
81
+ </a>
82
+ );
83
+ };
84
+
85
+ export const Ecosystem = ({
86
+ eyebrow,
87
+ headline,
88
+ cards,
89
+ }: EcosystemContent): JSX.Element => (
90
+ <Section
91
+ id="ecosystem"
92
+ className="pt-[112px] pb-[144px] border-t border-white/5"
93
+ >
94
+ <div className="mx-auto mb-[88px] max-w-[1180px] text-center">
95
+ <span className="font-label text-[11px] font-semibold uppercase tracking-[0.24em] text-accent">
96
+ {eyebrow}
97
+ </span>
98
+ <h2 className="mt-5 font-display text-[clamp(34px,4.4vw,60px)] font-[380] leading-[1.04] tracking-[-0.02em] [font-variation-settings:'opsz'_96]">
99
+ {renderHighlightedText(headline, HIGHLIGHT_CLS)}
100
+ </h2>
101
+ </div>
102
+ <div className="mx-auto grid max-w-[1180px] grid-cols-3 gap-16 max-[768px]:grid-cols-1 max-[768px]:gap-7">
103
+ {cards.map((card) => (
104
+ <Card key={card.suffix} card={card} />
105
+ ))}
106
+ </div>
107
+ </Section>
108
+ );
package/src/Footer.tsx CHANGED
@@ -2,6 +2,7 @@ import type { JSX } from "preact";
2
2
  import { cn } from "./cn";
3
3
  import type { RizomBrandSuffix, RizomFooterTagline, RizomLink } from "./types";
4
4
  import { GUTTER } from "./Section";
5
+ import { Wordmark } from "./Wordmark";
5
6
 
6
7
  const LINK_CLS =
7
8
  "text-label-md text-theme-light hover:text-theme transition-colors";
@@ -32,11 +33,7 @@ export const Footer = ({
32
33
  >
33
34
  <div className="flex flex-col items-center gap-1.5 md:items-start max-w-[560px]">
34
35
  <div className="flex flex-col items-center gap-1.5 md:flex-row md:items-center md:gap-3">
35
- <span className="font-nav text-[15px]">
36
- <span className="font-bold">rizom</span>
37
- <span className="font-bold text-accent">.</span>
38
- <span className="text-theme-muted">{brandSuffix}</span>
39
- </span>
36
+ <Wordmark brandSuffix={brandSuffix} className="text-[16px]" />
40
37
  <span className="text-label-md text-theme-light">{metaLabel}</span>
41
38
  </div>
42
39
  {tagline ? (
package/src/Header.tsx CHANGED
@@ -1,5 +1,6 @@
1
1
  import type { JSX } from "preact";
2
2
  import type { RizomBrandSuffix, RizomLink } from "./types";
3
+ import { Wordmark } from "./Wordmark";
3
4
 
4
5
  const LINK_CLS =
5
6
  "hidden md:inline-block font-body text-[15px] text-theme-muted hover:text-theme transition-colors relative py-1 after:content-[''] after:absolute after:left-0 after:bottom-0 after:h-px after:w-0 after:bg-accent after:transition-all after:duration-300 hover:after:w-full";
@@ -16,11 +17,7 @@ export const Header = ({
16
17
  primaryCta,
17
18
  }: HeaderProps): JSX.Element => (
18
19
  <nav className="fixed top-0 left-0 right-0 z-[100] flex items-center justify-between bg-nav-fade px-6 py-4 backdrop-blur-[8px] md:px-10 md:py-5 xl:px-20">
19
- <div className="flex items-center gap-0 font-nav text-[20px]">
20
- <span className="font-bold text-theme">rizom</span>
21
- <span className="font-bold text-accent">.</span>
22
- <span className="text-theme-muted">{brandSuffix}</span>
23
- </div>
20
+ <Wordmark brandSuffix={brandSuffix} className="text-[22px]" />
24
21
  <div className="flex items-center gap-3 md:gap-8">
25
22
  {navLinks.map((link) => (
26
23
  <a key={link.href} href={link.href} className={LINK_CLS}>
@@ -0,0 +1,32 @@
1
+ import type { JSX } from "preact";
2
+ import { cn } from "./cn";
3
+ import type { RizomBrandSuffix } from "./types";
4
+
5
+ export interface WordmarkProps {
6
+ brandSuffix: RizomBrandSuffix;
7
+ className?: string;
8
+ dotClassName?: string;
9
+ }
10
+
11
+ const DOT_BY_SUFFIX: Record<RizomBrandSuffix, string> = {
12
+ work: "text-accent",
13
+ foundation: "text-secondary",
14
+ ai: "text-accent-bright",
15
+ };
16
+
17
+ export const Wordmark = ({
18
+ brandSuffix,
19
+ className,
20
+ dotClassName,
21
+ }: WordmarkProps): JSX.Element => (
22
+ <span
23
+ className={cn(
24
+ "inline-flex items-baseline gap-0 font-display font-medium tracking-[-0.015em] [font-variation-settings:'opsz'_24]",
25
+ className,
26
+ )}
27
+ >
28
+ <span className="text-theme">rizom</span>
29
+ <span className={cn(DOT_BY_SUFFIX[brandSuffix], dotClassName)}>.</span>
30
+ <span className="italic font-normal text-theme-muted">{brandSuffix}</span>
31
+ </span>
32
+ );
package/src/index.ts CHANGED
@@ -23,6 +23,12 @@ export { SideNav } from "./SideNav";
23
23
 
24
24
  export { renderHighlightedText } from "./highlighted-text";
25
25
 
26
+ export { Wordmark } from "./Wordmark";
27
+ export type { WordmarkProps } from "./Wordmark";
28
+
29
+ export { Ecosystem } from "./Ecosystem";
30
+ export type { EcosystemCard, EcosystemContent } from "./Ecosystem";
31
+
26
32
  export type {
27
33
  ProductCardContent,
28
34
  ProductVariant,