feat(site): redesign with product pages, ecosystem sections and pixel reveal

Add cli/code/office/platform/pricing pages, new home sections
(Ecosystem, FeatureGrid, Faq, WorkflowSteps, BottomCta, ProductEcosystem),
ScrollReveal and PixelTextReveal animation components, brand assets,
and expanded site-content.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
Leon-in
2026-05-30 14:00:18 +08:00
parent 3213f00b7b
commit 97db9ee8c7
27 changed files with 1709 additions and 32 deletions
+1 -1
View File
@@ -17,7 +17,7 @@ export default function Footer() {
<div className="footer-top">
<div className="footer-logo-wrapper">
<Link href="/" className="logo-link w-inline-block w--current">
<Image src="/assets/wubflow-shield-nocodexport-dev/68a342b7066c56fa60eb3af1/68a73cf7c58867b86184dc28_logo-icon-quantum-webflow-template.svg" width={54} height={54} alt="DAL Code logo" className="logo-icon w-variant-7662d6cb-8aa5-f783-c60a-07a613bd9733" />
<Image src="/assets/dalcode-logo-dark.svg" width={54} height={54} alt="DAL Code" className="logo-icon" />
</Link>
</div>
<Link href="/contact" className="footer-button w-inline-block">
+4 -2
View File
@@ -6,6 +6,7 @@ import Link from "next/link"
import { usePathname } from "next/navigation"
import { useTranslations } from "next-intl"
import ThemeToggle from "@/components/ThemeToggle"
import LocaleSwitcher from "@/components/LocaleSwitcher"
import { NAV_GROUPS, NAV_LINKS } from "@/lib/site-content"
function ChevronIcon() {
@@ -57,12 +58,12 @@ export default function Header() {
<div className="header-logo-wrapper">
<div className="show-light-mode">
<Link href="/" className="logo-link w-inline-block">
<Image src="/assets/wubflow-shield-nocodexport-dev/68a342b7066c56fa60eb3af1/68a43b922d3d1ca923f36385_logo-icon-quantum-webflow-template.svg" width={54} height={54} alt="Logo" className="logo-icon" />
<Image src="/assets/dalcode-app-icon.svg" width={54} height={54} alt="DAL Code" className="logo-icon" />
</Link>
</div>
<div className="show-dark-mode">
<Link href="/" className="logo-link w-inline-block">
<Image src="/assets/wubflow-shield-nocodexport-dev/68a342b7066c56fa60eb3af1/68a73cf7c58867b86184dc28_logo-icon-quantum-webflow-template.svg" width={54} height={54} alt="Logo" className="logo-icon" />
<Image src="/assets/dalcode-logo-dark.svg" width={54} height={54} alt="DAL Code" className="logo-icon" />
</Link>
</div>
</div>
@@ -171,6 +172,7 @@ export default function Header() {
</div>
</div>
<ThemeToggle />
<LocaleSwitcher />
<button
className={`hamburger-menu w-nav-button ${mobileOpen ? "w--open" : ""}`}
onClick={toggleMobile}
+150
View File
@@ -0,0 +1,150 @@
"use client"
import { useRef, useEffect } from "react"
interface PixelTextRevealProps {
lines?: string[]
className?: string
}
export default function PixelTextReveal({
lines = ["DAL", "Ecosystem"],
className,
}: PixelTextRevealProps) {
const canvasRef = useRef<HTMLCanvasElement>(null)
useEffect(() => {
const canvas = canvasRef.current
if (!canvas) return
const ctx = canvas.getContext("2d")
if (!ctx) return
const drawCtx = ctx
const dpr = window.devicePixelRatio || 1
const width = canvas.clientWidth
const height = canvas.clientHeight
canvas.width = width * dpr
canvas.height = height * dpr
ctx.scale(dpr, dpr)
const cellSize = 5
const gap = 1.5
const step = cellSize + gap
const cols = Math.floor(width / step)
const rows = Math.floor(height / step)
const scale = 6
const offW = cols * scale
const offH = rows * scale
const offscreen = document.createElement("canvas")
offscreen.width = offW
offscreen.height = offH
const offCtx = offscreen.getContext("2d")!
offCtx.fillStyle = "#000"
offCtx.fillRect(0, 0, offW, offH)
offCtx.fillStyle = "#fff"
offCtx.textAlign = "center"
offCtx.textBaseline = "middle"
const primarySize = Math.max(48, Math.floor(offH * 0.38))
const secondarySize = Math.max(36, Math.floor(offH * 0.26))
const lineGap = Math.floor(offH * 0.06)
const totalH = primarySize + (lines.length > 1 ? secondarySize + lineGap : 0)
const baseY = (offH - totalH) / 2
lines.forEach((line, i) => {
const size = i === 0 ? primarySize : secondarySize
offCtx.font = `${i === 0 ? 900 : 800} ${size}px "Inter", "SF Pro Display", system-ui, sans-serif`
offCtx.letterSpacing = i === 0 ? "0.05em" : "0.02em"
const y = i === 0
? baseY + primarySize / 2
: baseY + primarySize + lineGap + secondarySize / 2
offCtx.fillText(line, offW / 2, y)
})
const imgData = offCtx.getImageData(0, 0, offW, offH)
const textMap: boolean[][] = []
for (let gy = 0; gy < rows; gy++) {
textMap[gy] = []
for (let gx = 0; gx < cols; gx++) {
let sum = 0
for (let sy = 0; sy < scale; sy++) {
for (let sx = 0; sx < scale; sx++) {
sum += imgData.data[((gy * scale + sy) * offW + gx * scale + sx) * 4]
}
}
textMap[gy][gx] = sum / (scale * scale) > 60
}
}
const centerX = cols / 2
const centerY = rows / 2
const cells = Array.from({ length: rows }, (_, y) =>
Array.from({ length: cols }, (_, x) => {
const isText = textMap[y][x]
const dist = Math.hypot(x - centerX, y - centerY)
return {
opacity: 0,
target: isText ? 1.0 : 0.006 + Math.random() * 0.014,
delay: isText
? dist * 12 + Math.random() * 200
: Math.random() * 600,
isText,
}
})
)
let fg = document.documentElement.classList.contains("dark")
? "255,255,255"
: "5,5,5"
const observer = new MutationObserver(() => {
fg = document.documentElement.classList.contains("dark")
? "255,255,255"
: "5,5,5"
})
observer.observe(document.documentElement, {
attributes: true,
attributeFilter: ["class"],
})
const startTime = performance.now()
let raf: number
function draw(now: number) {
const elapsed = now - startTime
drawCtx.clearRect(0, 0, width, height)
for (let y = 0; y < rows; y++) {
for (let x = 0; x < cols; x++) {
const c = cells[y][x]
if (elapsed > c.delay) {
c.opacity += (c.target - c.opacity) * 0.06
}
if (c.opacity < 0.004) continue
drawCtx.fillStyle = `rgba(${fg},${c.opacity})`
drawCtx.fillRect(x * step, y * step, cellSize, cellSize)
}
}
raf = requestAnimationFrame(draw)
}
raf = requestAnimationFrame(draw)
return () => {
cancelAnimationFrame(raf)
observer.disconnect()
}
}, [lines])
return (
<canvas
ref={canvasRef}
className={className}
style={{ width: "100%", height: "100%", display: "block" }}
/>
)
}
+42
View File
@@ -0,0 +1,42 @@
"use client"
import { useEffect, useRef } from "react"
interface ScrollRevealProps {
children: React.ReactNode
className?: string
delay?: number
}
export default function ScrollReveal({
children,
className = "",
delay = 0,
}: ScrollRevealProps) {
const ref = useRef<HTMLDivElement>(null)
useEffect(() => {
const el = ref.current
if (!el) return
const observer = new IntersectionObserver(
([entry]) => {
if (entry.isIntersecting) {
setTimeout(() => {
el.classList.add("reveal-visible")
}, delay)
observer.unobserve(el)
}
},
{ threshold: 0.1 },
)
observer.observe(el)
return () => observer.disconnect()
}, [delay])
return (
<div ref={ref} className={`reveal-up ${className}`}>
{children}
</div>
)
}
+1 -1
View File
@@ -28,7 +28,7 @@ export default function MissionSection() {
</div>
<Link href="/contact" className="tertiary-button w-inline-block">
<div className="button-content">
<div></div>
<div></div>
<div className="button-icon-wrapper secondary">
<svg
xmlns="http://www.w3.org/2000/svg"
+13 -3
View File
@@ -1,4 +1,3 @@
import Image from "next/image"
import Link from "next/link"
import { BLOG_POSTS } from "@/lib/blog-data"
@@ -42,8 +41,19 @@ export default function BlogPreviewSection() {
<div className="blog-featured-v1-wrapper">
<div className="border-wrapper">
<Link href={`/blog-posts/${post.slug}`} className="blog-card-v1 w-inline-block">
<div className="blog-v1-image-wrapper">
<Image alt={post.imageAlt} src={post.image} sizes="(max-width: 767px) 100vw, (max-width: 991px) 95vw, 939.96533203125px" className="image" fill style={{ objectFit: "cover" }} />
<div className="blog-v1-image-wrapper" style={{
background: "linear-gradient(135deg, var(--core--colors--neutral--200) 0%, var(--core--colors--neutral--300) 100%)",
display: "flex",
alignItems: "center",
justifyContent: "center",
}}>
<span style={{
fontSize: "0.75rem",
fontWeight: 600,
letterSpacing: "0.08em",
textTransform: "uppercase",
color: "var(--core--colors--neutral--500)",
}}>{post.category}</span>
</div>
<div className="blog-v1-content">
<div className="inner-container _420px">
+60
View File
@@ -0,0 +1,60 @@
import Link from "next/link"
import LottiePlayer from "@/components/LottiePlayer"
export default function BottomCta() {
return (
<section className="cta-section v1">
<div className="w-layout-blockcontainer container-default position-relative---z-index-1 w-container">
<div className="inner-container _430px">
<div className="subtitle">Get Started</div>
<div className="mg-top-3x-extra-small">
<h2 className="text-titles-dm">
</h2>
</div>
<div className="mg-top-4x-extra-small">
<p className="text-paragraph-dm">
Lead CTO
</p>
</div>
<div className="mg-top-2x-extra-small">
<div className="buttons-row left">
<Link
href="/contact"
className="secondary-button w-inline-block"
>
<div className="button-content">
<div></div>
<div className="button-icon-wrapper secondary">
<svg
xmlns="http://www.w3.org/2000/svg"
width="100%"
viewBox="0 0 17 17"
fill="none"
className="squared-icon"
>
<path
d="M6.25391 3.45312L10.7458 8.01563L6.25391 12.5781"
stroke="currentColor"
strokeWidth="1.5"
strokeLinecap="square"
/>
</svg>
<div className="button-icon-bg bg-neutral-800" />
<div className="button-icon-bg-inside bg-neutral-600" />
</div>
</div>
</Link>
</div>
</div>
</div>
</div>
<LottiePlayer
src="/assets/cdn-prod-website-files-com/68a342b7066c56fa60eb3af1/68d1df78b3b45295434b5c6a_cta-animation-waterfall.json"
className="cta-image"
loop
autoplay
/>
</section>
)
}
+96
View File
@@ -0,0 +1,96 @@
import { PLATFORM_ADVANTAGES } from "@/lib/site-content"
export default function EcosystemSection() {
return (
<section className="section bg-neutral overflow-hidden">
<div className="w-layout-blockcontainer container-default w-container">
<div
data-w-id="eco-title"
style={{ opacity: "0", filter: "blur(8px)" }}
className="text-center"
>
<div className="subtitle">Platform</div>
<div className="mg-top-4x-extra-small">
<h2>DeepAILab AI </h2>
</div>
<div className="mg-top-4x-extra-small">
<p>
线
</p>
</div>
</div>
<div className="mg-top-large">
<div
data-w-id="eco-cards"
style={{ opacity: "0", filter: "blur(8px)" }}
className="corner-gradient-container"
>
<div className="border-wrapper">
<div className="w-layout-grid principles-grid">
{PLATFORM_ADVANTAGES.map((adv) => (
<div key={adv.title} className="card principles-card">
<div>
<h3 className="display-4">{adv.title}</h3>
<div className="mg-top-5x-extra-small">
<p>{adv.description}</p>
</div>
</div>
</div>
))}
</div>
</div>
<div
data-wf--corner-gradient-outline--variant="base"
className="corner-gradient-wrapper"
>
<div className="corner-gradient-horizontal top-left" />
<div className="corner-gradient-horizontal bottom-left" />
<div className="corner-gradient-horizontal top-right" />
<div className="corner-gradient-horizontal bottom-right" />
<div className="corner-gradient-vertical bottom-left" />
<div className="corner-gradient-vertical bottom-right" />
<div className="corner-gradient-vertical top-left" />
<div className="corner-gradient-vertical top-right" />
</div>
</div>
</div>
<div className="mg-top-regular">
<div
data-w-id="eco-cta"
style={{ opacity: "0", filter: "blur(8px)" }}
className="buttons-row"
>
<a
href="https://deepailab.com"
target="_blank"
rel="noopener noreferrer"
className="secondary-button w-inline-block"
>
<div className="button-content">
<div> DeepAILab </div>
<div className="button-icon-wrapper secondary">
<svg
xmlns="http://www.w3.org/2000/svg"
width="100%"
viewBox="0 0 17 17"
fill="none"
className="squared-icon"
>
<path
d="M6.25391 3.45312L10.7458 8.01563L6.25391 12.5781"
stroke="currentColor"
strokeWidth="1.5"
strokeLinecap="square"
/>
</svg>
<div className="button-icon-bg bg-neutral-800" />
<div className="button-icon-bg-inside bg-neutral-600" />
</div>
</div>
</a>
</div>
</div>
</div>
</section>
)
}
+76
View File
@@ -0,0 +1,76 @@
"use client"
import { useState } from "react"
import { HOME_FAQS } from "@/lib/site-content"
export default function FaqSection() {
const [openIndex, setOpenIndex] = useState<number | null>(null)
return (
<section className="section overflow-hidden">
<div className="w-layout-blockcontainer container-default w-container">
<div
data-w-id="faq-wrapper"
style={{ opacity: "0", filter: "blur(8px)" }}
className="w-layout-grid faqs-v1-wrapper"
>
<div>
<div className="subtitle">FAQ</div>
<div className="mg-top-4x-extra-small">
<h2></h2>
</div>
</div>
<div className="w-layout-grid faqs-v1-grid" role="list">
{HOME_FAQS.map((faq, i) => (
<div
key={faq.question}
className="card accordion-card-v1"
role="listitem"
style={{ cursor: "pointer" }}
onClick={() => setOpenIndex(openIndex === i ? null : i)}
>
<div className="accordion-number">
{String(i + 1).padStart(2, "0")}
</div>
<div className="accordion-body">
<div className="accordion-title">{faq.question}</div>
<div
className="accordion-content"
style={{
maxHeight: openIndex === i ? "200px" : "0",
overflow: "hidden",
transition: "max-height 0.3s ease-out",
opacity: openIndex === i ? 1 : 0,
}}
>
<p>{faq.answer}</p>
</div>
</div>
<div className="accordion-arrow">
<svg
xmlns="http://www.w3.org/2000/svg"
width="100%"
viewBox="0 0 16 16"
fill="none"
style={{
transform: openIndex === i ? "rotate(180deg)" : "rotate(0deg)",
transition: "transform 0.3s ease-out",
}}
>
<path
d="M4 6L8 10L12 6"
stroke="currentColor"
strokeWidth="1.5"
strokeLinecap="round"
strokeLinejoin="round"
/>
</svg>
</div>
</div>
))}
</div>
</div>
</div>
</section>
)
}
+44
View File
@@ -0,0 +1,44 @@
import { FEATURE_ITEMS } from "@/lib/site-content"
export default function FeatureGrid() {
return (
<section className="section overflow-hidden">
<div className="w-layout-blockcontainer container-default w-container">
<div
data-w-id="feature-title"
style={{ opacity: "0", filter: "blur(8px)" }}
className="text-center"
>
<div className="subtitle">Core Capabilities</div>
<div className="mg-top-4x-extra-small">
<h2> prompt </h2>
</div>
<div className="mg-top-4x-extra-small">
<p>
</p>
</div>
</div>
<div className="mg-top-large">
<div
data-w-id="feature-grid"
style={{ opacity: "0", filter: "blur(8px)" }}
>
<div className="w-layout-grid values-grid" style={{ gridTemplateColumns: "1fr 1fr 1fr" }}>
{FEATURE_ITEMS.map((item) => (
<div key={item.title} className="value-item">
<div>
<h3 className="display-4">{item.title}</h3>
<div className="mg-top-5x-extra-small">
<p style={{ fontSize: "0.875rem" }}>{item.description}</p>
</div>
</div>
</div>
))}
</div>
</div>
</div>
</div>
</section>
)
}
+17 -9
View File
@@ -1,6 +1,5 @@
import Image from "next/image"
import Link from "next/link"
import LottiePlayer from "@/components/LottiePlayer"
import PixelTextReveal from "@/components/PixelTextReveal"
export default function HeroSection() {
return (
@@ -67,7 +66,7 @@ export default function HeroSection() {
<div className="hero-v1-bg-gradient" />
</div>
</div>
<LottiePlayer src="/assets/cdn-prod-website-files-com/68a342b7066c56fa60eb3af1/68d1a7d9c54a9b73191bb531_hero-v1-animation-quantum-webflow-template.json" className="hero-v1-lottie" loop autoplay />
<PixelTextReveal lines={["DAL", "Ecosystem"]} className="hero-v1-lottie" />
</div>
<div id="about-us" data-w-id="bce231a0-6e79-c8d3-8883-56d99499b3ad" style={{ opacity: "0", filter: "blur(8px)" }} className="about-section-wrapper">
<div className="about-section-top-content">
@@ -82,13 +81,22 @@ export default function HeroSection() {
</div>
<div className="about-section-bottom-content">
<Link href="/about" className="lightbox-link w-inline-block">
<Image
src="/assets/wubflow-shield-nocodexport-dev/68a342b7066c56fa60eb3af1/68a612636043d8e5dcb04ad0_about-us-video-thumbnail-quantum-webflow-template.jpg"
width={660}
height={372}
alt="DAL Code product overview"
<div
className="lightbox-thumbnail"
/>
style={{
width: 660,
height: 372,
background: "linear-gradient(135deg, var(--core--colors--neutral--200) 0%, var(--core--colors--neutral--300) 100%)",
display: "flex",
alignItems: "center",
justifyContent: "center",
fontSize: "0.875rem",
color: "var(--core--colors--neutral--500)",
letterSpacing: "0.05em",
}}
>
PRODUCT DEMO
</div>
</Link>
<div className="position-relative---z-index-1">
<div className="hidden-on-mobile-portrait">
+61 -13
View File
@@ -1,34 +1,82 @@
import Image from "next/image"
import { INTEGRATION_ITEMS } from "@/lib/site-content"
const ECOSYSTEM_ITEMS = [
"DAL Code",
"DAL CLI",
"DAL Office",
"API Platform",
"Intent Capture",
"Mission Mode",
"Smart Routing",
"Skills Engine",
"Context Compression",
"Diff Review",
"BYOK",
"Private Deploy",
]
const MARQUEE_ROWS = Array.from({ length: 3 }, () => INTEGRATION_ITEMS)
const MARQUEE_ROWS = [ECOSYSTEM_ITEMS, ECOSYSTEM_ITEMS, ECOSYSTEM_ITEMS]
export default function IntegrationsSection() {
return (
<section className="section-small bg-neutral overflow-hidden">
<div className="w-layout-blockcontainer container-default w-container">
<div data-w-id="ee652702-222a-0ca5-2508-17b1a107582a" style={{ opacity: "0", filter: "blur(8px)" }} className="title-left-content-right">
<div
data-w-id="ee652702-222a-0ca5-2508-17b1a107582a"
style={{ opacity: "0", filter: "blur(8px)" }}
className="title-left-content-right"
>
<div className="inner-container _400px _100-tablet">
<div className="subtitle">Work Surfaces</div>
<div className="subtitle">Ecosystem</div>
<div className="mg-top-4x-extra-small">
<h2></h2>
<h2>线</h2>
</div>
</div>
<div className="inner-container _400px _100-tablet">
<p>
DAL Code Desktop IDEWeb WorkspaceMobile ReviewMission PlannerRAGToolsDiff
IDEAPI
</p>
</div>
</div>
<div className="mg-top-regular">
<div data-w-id="f6559b35-9557-2504-f076-3a36fa5775a3" style={{ opacity: "0", filter: "blur(8px)" }} className="integrations-marquee-wrapper marquee-hover-stop" {...{ "tr-marquee-speed": "50", "tr-marquee-element": "component", "tr-marquee-scrolldirection": "true", "tr-marquee-scrollscrub": "false" }}>
<div
data-w-id="f6559b35-9557-2504-f076-3a36fa5775a3"
style={{ opacity: "0", filter: "blur(8px)" }}
className="integrations-marquee-wrapper marquee-hover-stop"
{...{
"tr-marquee-speed": "40",
"tr-marquee-element": "component",
"tr-marquee-scrolldirection": "true",
"tr-marquee-scrollscrub": "false",
}}
>
{MARQUEE_ROWS.map((items, rowIndex) => (
<div key={rowIndex} className="integrations-marquee marquee-scroll-item">
{items.map((item) => (
<a key={`${rowIndex}-${item.label}`} href="/about" className="integration-marquee-item w-inline-block">
<Image src={item.icon} width={94} height={94} alt={item.label} style={{ filter: "invert(0%)" }} className="integration-marquee-item-image" />
<div style={{ width: "0%", height: "100%" }} className="integration-marquee-item-bg" />
</a>
{items.map((label, i) => (
<div
key={`${rowIndex}-${i}`}
className="integration-marquee-item"
style={{
display: "flex",
alignItems: "center",
justifyContent: "center",
padding: "12px 24px",
}}
>
<span
style={{
fontSize: "0.875rem",
fontWeight: 600,
letterSpacing: "0.04em",
whiteSpace: "nowrap",
color: "var(--font--colors--paragraph)",
}}
>
{label}
</span>
<div
style={{ width: "0%", height: "100%" }}
className="integration-marquee-item-bg"
/>
</div>
))}
</div>
))}
+91
View File
@@ -0,0 +1,91 @@
import Link from "next/link"
import { PRODUCT_ITEMS } from "@/lib/site-content"
export default function ProductEcosystem() {
return (
<section className="section overflow-hidden">
<div className="w-layout-blockcontainer container-default w-container">
<div
data-w-id="prod-eco-title"
style={{ opacity: "0", filter: "blur(8px)" }}
className="text-center"
>
<div className="subtitle">Product Ecosystem</div>
<div className="mg-top-4x-extra-small">
<h2>线</h2>
</div>
<div className="mg-top-4x-extra-small">
<p>
IDEAPI
</p>
</div>
</div>
<div className="mg-top-large">
<div
data-w-id="prod-eco-grid"
style={{ opacity: "0", filter: "blur(8px)" }}
className="corner-gradient-container"
>
<div className="border-wrapper">
<div
className="w-layout-grid"
style={{ gridTemplateColumns: "1fr 1fr" }}
>
{PRODUCT_ITEMS.map((product) => (
<Link
key={product.name}
href={product.href}
className="card principles-card w-inline-block"
style={{ textDecoration: "none" }}
>
<div>
<div className="subtitle" style={{ fontSize: "0.75rem" }}>
{product.name}
</div>
<h3 className="display-4">{product.tagline}</h3>
<div className="mg-top-5x-extra-small">
<p>{product.description}</p>
</div>
<div
className="mg-top-4x-extra-small"
style={{ display: "flex", flexWrap: "wrap", gap: "6px" }}
>
{product.features.map((f) => (
<span
key={f}
style={{
padding: "2px 8px",
fontSize: "0.75rem",
border: "1px solid var(--core--colors--neutral--400)",
borderRadius: "4px",
color: "var(--font--colors--paragraph)",
}}
>
{f}
</span>
))}
</div>
</div>
</Link>
))}
</div>
</div>
<div
data-wf--corner-gradient-outline--variant="base"
className="corner-gradient-wrapper"
>
<div className="corner-gradient-horizontal top-left" />
<div className="corner-gradient-horizontal bottom-left" />
<div className="corner-gradient-horizontal top-right" />
<div className="corner-gradient-horizontal bottom-right" />
<div className="corner-gradient-vertical bottom-left" />
<div className="corner-gradient-vertical bottom-right" />
<div className="corner-gradient-vertical top-left" />
<div className="corner-gradient-vertical top-right" />
</div>
</div>
</div>
</div>
</section>
)
}
+75
View File
@@ -0,0 +1,75 @@
import { WORKFLOW_ITEMS } from "@/lib/site-content"
export default function WorkflowSteps() {
return (
<section className="section bg-neutral overflow-hidden">
<div className="w-layout-blockcontainer container-default w-container">
<div
data-w-id="workflow-title"
style={{ opacity: "0", filter: "blur(8px)" }}
className="title-left-content-right"
>
<div className="inner-container _400px _100-tablet">
<div className="subtitle">How It Works</div>
<div className="mg-top-4x-extra-small">
<h2></h2>
</div>
</div>
<div className="inner-container _400px _100-tablet">
<p>
AI promptDAL Code AI 访
</p>
</div>
</div>
<div className="mg-top-large">
<div
data-w-id="workflow-cards"
style={{ opacity: "0", filter: "blur(8px)" }}
className="corner-gradient-container"
>
<div className="border-wrapper">
<div className="w-layout-grid principles-grid">
{WORKFLOW_ITEMS.map((step) => (
<div key={step.number} className="card principles-card">
<div
style={{
fontSize: "3rem",
fontWeight: 700,
lineHeight: 1,
color: "var(--core--colors--neutral--400)",
}}
>
{step.number}
</div>
<div>
<div className="subtitle" style={{ fontSize: "0.75rem" }}>
{step.name}
</div>
<h3 className="display-4">{step.title}</h3>
<div className="mg-top-5x-extra-small">
<p>{step.description}</p>
</div>
</div>
</div>
))}
</div>
</div>
<div
data-wf--corner-gradient-outline--variant="base"
className="corner-gradient-wrapper"
>
<div className="corner-gradient-horizontal top-left" />
<div className="corner-gradient-horizontal bottom-left" />
<div className="corner-gradient-horizontal top-right" />
<div className="corner-gradient-horizontal bottom-right" />
<div className="corner-gradient-vertical bottom-left" />
<div className="corner-gradient-vertical bottom-right" />
<div className="corner-gradient-vertical top-left" />
<div className="corner-gradient-vertical top-right" />
</div>
</div>
</div>
</div>
</section>
)
}
+6
View File
@@ -1,5 +1,11 @@
export { default as BlogPreviewSection } from "./BlogPreviewSection"
export { default as BottomCta } from "./BottomCta"
export { default as CtaSection } from "./CtaSection"
export { default as EcosystemSection } from "./EcosystemSection"
export { default as FaqSection } from "./FaqSection"
export { default as FeatureGrid } from "./FeatureGrid"
export { default as HeroSection } from "./HeroSection"
export { default as IntegrationsSection } from "./IntegrationsSection"
export { default as PrinciplesSection } from "./PrinciplesSection"
export { default as ProductEcosystem } from "./ProductEcosystem"
export { default as WorkflowSteps } from "./WorkflowSteps"