Skip to content

Commit ac2301a

Browse files
V48 (impl-only): Align hero CTAs under pillars and trim capability chips to three
Use a single-row chip set (Synthesize Options, Deposit AssetPacks, Buy AssetPacks) and place each colored CTA directly under its Sell/Buy/Settle card column.
1 parent f06e9ab commit ac2301a

3 files changed

Lines changed: 52 additions & 39 deletions

File tree

uapi/components/bitcode/layout/BitcodePublicCopy/bitcode-public-copy.ts

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,9 @@ export const BITCODE_PUBLIC_COPY = {
44
description:
55
'Make AssetPacks from source-code, exposing only IP you confirm, to deposit them for purchase. Buy AssetPacks with Bitcoin to consume the specific knowledge you request. All running on fully open-source, proven, and ledgerized infrastructure.',
66
capabilityChips: [
7-
'SELL ASSETPACKS',
8-
'BUY WITH NEED',
9-
'BTC SETTLEMENT',
10-
'PROOF READBACK',
7+
'Synthesize Options',
8+
'Deposit AssetPacks',
9+
'Buy AssetPacks',
1110
],
1211
primaryCta: {
1312
href: '/reads',

uapi/components/marketing/MarketingLandingHero/MarketingLandingHero.tsx

Lines changed: 45 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,31 @@ import {
1919
productPillars,
2020
} from '@/components/marketing/MarketingLandingShared/MarketingLandingShared';
2121

22+
/** CTA under each pillar — order and colors match Sell · Buy · Settle columns. */
23+
const pillarCtas = [
24+
{
25+
pillarTitle: 'Sell',
26+
href: BITCODE_PUBLIC_COPY.secondaryCta.href,
27+
label: BITCODE_PUBLIC_COPY.secondaryCta.label,
28+
className:
29+
'border-fuchsia-300/28 bg-fuchsia-500/12 text-fuchsia-50 hover:border-fuchsia-300/48 hover:bg-fuchsia-500/18',
30+
},
31+
{
32+
pillarTitle: 'Buy',
33+
href: BITCODE_PUBLIC_COPY.primaryCta.href,
34+
label: BITCODE_PUBLIC_COPY.primaryCta.label,
35+
className:
36+
'border-emerald-300/28 bg-emerald-400/12 text-emerald-50 hover:border-emerald-300/48 hover:bg-emerald-400/18',
37+
},
38+
{
39+
pillarTitle: 'Settle',
40+
href: BITCODE_PUBLIC_COPY.tertiaryCta.href,
41+
label: BITCODE_PUBLIC_COPY.tertiaryCta.label,
42+
className:
43+
'border-orange-300/28 bg-orange-400/12 text-orange-50 hover:border-orange-300/48 hover:bg-orange-400/18',
44+
},
45+
] as const;
46+
2247
export const MarketingLandingHero = memo(function MarketingLandingHero() {
2348
return (
2449
<motion.section
@@ -51,11 +76,11 @@ export const MarketingLandingHero = memo(function MarketingLandingHero() {
5176
</p>
5277
</div>
5378

54-
<div className="mt-4 flex flex-wrap gap-2 text-[11px] uppercase tracking-[0.22em] text-emerald-200/68 phone:mt-5">
79+
<div className="mt-4 flex flex-nowrap gap-2 overflow-x-auto text-[11px] uppercase tracking-[0.18em] text-emerald-200/68 phone:mt-5 phone:tracking-[0.22em]">
5580
{BITCODE_PUBLIC_COPY.capabilityChips.map((item) => (
5681
<span
5782
key={item}
58-
className="relative overflow-hidden rounded-none border border-cyan-200/18 bg-[linear-gradient(135deg,rgba(9,22,48,0.82),rgba(18,49,88,0.38))] px-3 py-2 text-cyan-100 shadow-[0_12px_28px_rgba(6,182,212,0.08)] backdrop-blur-md"
83+
className="relative shrink-0 overflow-hidden rounded-none border border-cyan-200/18 bg-[linear-gradient(135deg,rgba(9,22,48,0.82),rgba(18,49,88,0.38))] px-3 py-2 text-cyan-100 shadow-[0_12px_28px_rgba(6,182,212,0.08)] backdrop-blur-md"
5984
>
6085
<span
6186
className="absolute inset-0 opacity-30"
@@ -66,40 +91,29 @@ export const MarketingLandingHero = memo(function MarketingLandingHero() {
6691
/>
6792
<span className="absolute inset-0 bg-[radial-gradient(circle_at_top_right,rgba(103,254,183,0.16),transparent_32%),radial-gradient(circle_at_bottom_left,rgba(56,189,248,0.12),transparent_34%)]" />
6893
<span className="absolute inset-[1px] rounded-none border border-white/8" />
69-
<span className="relative">{item}</span>
94+
<span className="relative whitespace-nowrap">{item}</span>
7095
</span>
7196
))}
7297
</div>
7398

74-
<div className="mt-4 grid grid-cols-1 gap-2 phone:mt-5 phone:grid-cols-2 phone:gap-3 desktop:grid-cols-3">
75-
{productPillars.map((pillar, index) => (
76-
<MarketingLandingPillarCard key={pillar.title} {...pillar} index={index} />
77-
))}
78-
</div>
99+
{/* Pillar + CTA share one column so each button sits under its card. */}
100+
<div className="mt-4 grid grid-cols-1 gap-x-2 gap-y-3 phone:mt-5 phone:grid-cols-2 phone:gap-x-3 desktop:grid-cols-3">
101+
{productPillars.map((pillar, index) => {
102+
const cta = pillarCtas.find((entry) => entry.pillarTitle === pillar.title) ?? pillarCtas[index];
79103

80-
<div className="mt-4 flex flex-wrap items-center gap-3 phone:mt-5">
81-
{/* Colors match pillar columns: Sell purple · Buy green · Settle/View orange */}
82-
<Link
83-
href={BITCODE_PUBLIC_COPY.secondaryCta.href}
84-
className="inline-flex items-center gap-2 rounded-none border border-fuchsia-300/28 bg-fuchsia-500/12 px-4 py-2.5 text-[11px] font-semibold uppercase tracking-[0.18em] text-fuchsia-50 transition-colors hover:border-fuchsia-300/48 hover:bg-fuchsia-500/18"
85-
>
86-
{BITCODE_PUBLIC_COPY.secondaryCta.label}
87-
<ArrowRightIcon className="h-4 w-4" />
88-
</Link>
89-
<Link
90-
href={BITCODE_PUBLIC_COPY.primaryCta.href}
91-
className="inline-flex items-center gap-2 rounded-none border border-emerald-300/28 bg-emerald-400/12 px-4 py-2.5 text-[11px] font-semibold uppercase tracking-[0.18em] text-emerald-50 transition-colors hover:border-emerald-300/48 hover:bg-emerald-400/18"
92-
>
93-
{BITCODE_PUBLIC_COPY.primaryCta.label}
94-
<ArrowRightIcon className="h-4 w-4" />
95-
</Link>
96-
<Link
97-
href={BITCODE_PUBLIC_COPY.tertiaryCta.href}
98-
className="inline-flex items-center gap-2 rounded-none border border-orange-300/28 bg-orange-400/12 px-4 py-2.5 text-[11px] font-semibold uppercase tracking-[0.18em] text-orange-50 transition-colors hover:border-orange-300/48 hover:bg-orange-400/18"
99-
>
100-
{BITCODE_PUBLIC_COPY.tertiaryCta.label}
101-
<ArrowRightIcon className="h-4 w-4" />
102-
</Link>
104+
return (
105+
<div key={pillar.title} className="flex min-w-0 flex-col gap-3">
106+
<MarketingLandingPillarCard {...pillar} index={index} />
107+
<Link
108+
href={cta.href}
109+
className={`inline-flex w-full items-center justify-center gap-2 rounded-none border px-4 py-2.5 text-[11px] font-semibold uppercase tracking-[0.18em] transition-colors ${cta.className}`}
110+
>
111+
{cta.label}
112+
<ArrowRightIcon className="h-4 w-4" />
113+
</Link>
114+
</div>
115+
);
116+
})}
103117
</div>
104118

105119
<MarketingLandingGuideCard />

uapi/tests/marketingLandingPage.test.tsx

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -116,10 +116,10 @@ describe('MarketingLandingPage', () => {
116116
/Make AssetPacks from source-code, exposing only IP you confirm/i,
117117
),
118118
).toBeInTheDocument();
119-
expect(screen.getByText('SELL ASSETPACKS')).toBeInTheDocument();
120-
expect(screen.getByText('BUY WITH NEED')).toBeInTheDocument();
121-
expect(screen.getByText('BTC SETTLEMENT')).toBeInTheDocument();
122-
expect(screen.getByText('PROOF READBACK')).toBeInTheDocument();
119+
expect(screen.getByText('Synthesize Options')).toBeInTheDocument();
120+
expect(screen.getByText('Deposit AssetPacks')).toBeInTheDocument();
121+
// Chip + Buy CTA can both render; assert chip via exact case from capability chips.
122+
expect(screen.getAllByText(/Buy AssetPacks/i).length).toBeGreaterThan(0);
123123
expect(screen.getAllByText('Packs').length).toBeGreaterThan(0);
124124
expect(document.getElementById('bitcodeDemonstrationRoot')).toBeNull();
125125
expect(document.querySelector('iframe')).toBeNull();

0 commit comments

Comments
 (0)