Column

Design as Code, Code as Design — How We Rebuilt Giselle’s Site Without Figma

PUBLISHED

design-as-code-without-figma-cover

What Space Missions Taught Me About Making Things

“Test like you fly.”

NASA's golden rule: build and test your systems the same way you'll launch them. No dry runs. No final polish behind the curtain. Just get in the cockpit and go.

That mindset stuck with me. So when it came time to rebuild the service site for our product—Giselle, an AI agent builder—I didn't open Figma. I opened Zed.

We've always designed Giselle by building it live, in motion. So when we started the site renewal, it only made sense to create it in the same spirit—not as a spec, not as a mockup, but as a living thing.

So I built it myself. As a designer. No handoff. No static files. Just vibe coding in Zed, with a couple of AI agents riding shotgun.

Was it fast? Not really. Was it clean? Nope. But it was honest—and alive.

Before and after comparison of Giselle website redesign
Before: The website transformation through code-first design

That one-person experiment shifted something. But here's the thing—while I built the foundation as a designer, it was our engineers who elevated the quality to production standards. They optimized performance, refined the architecture, and transformed our SEO from practically invisible to genuinely competitive. What I started as a design exploration, they helped mature into something that could actually serve our users.

Code became our shared language, and the same approach is now reshaping Giselle's core UI—no more designing in isolation. We're designing by doing, by coding, by flying.

Code-First vs Figma-First

This redesign wasn’t just a visual update—it was a shift in how we build. No mockups. No handoffs. We designed in code, in motion. Not to polish the final output, but to shape it live—just like the product itself.

Here’s the contrast:

Figma-First Code-First
Strengths Fast exploration, easy feedback Real interactions, production fidelity
When to use Early concepts, layout planning UI polish, rich behavior
Team structure Hand-off driven Collaborative, blended roles

Designing this way wasn't always faster. But it was truer. It let us feel the product as we made it—and that made all the difference.

Building Live, Performing in Flow

Giselle moves fast. New features appear almost daily, thanks to our engineers who work like Disney Imagineers (Disney's creative engineers who blend technical mastery with artistic vision to bring impossible ideas to life). But our product design hadn't caught up to their innovations. So I focused on renewing our service site—creating something that could truly speak in the voice of the product they were crafting.

This time, I didn't open Figma. I opened Zed.

No mockups. No handoffs. Just live code, a blank screen, and intuition. If Giselle is built by trying and tweaking, the site should be, too.

I used v0 for UI components, Claude and our own agents for guidance, and what I can only describe as vibe coding. Code a little. Refresh. Adjust. Feel it in motion.

Here are some of the v0 components I generated during the process:

The "sticker peel" effect on our homepage graphics is a perfect example of this. I wanted something playful and tactile, a feeling a static mockup could never capture. Building interactive components like this requires managing state, position, and user events, which is where coding directly shines. For example, this is how we manage the dynamic styles for our draggable cards using React hooks.

const cardStyle: React.CSSProperties = useMemo(
  () => ({
    position: "absolute",
    left: position.x,
    top: position.y,
    touchAction: "none",
    transition: isDragging ? "none" : "all 0.3s ease",
    transform: isDragging ? "scale(1.05)" : "scale(1)",
    boxShadow: isDragging
      ? "0 25px 50px -12px rgba(0, 0, 0, 0.25)"
      : "0 10px 15px -3px rgba(0, 0, 0, 0.1)",
    zIndex: isDragging ? 10 : 1,
    cursor: isDragging ? "grabbing" : "grab",
  }),
  [position, isDragging],
);

This hands-on approach meant that when things inevitably broke—grids collapsing, spacing getting weird—I wasn't stuck. I’d ask an agent: "Why's this margin off?" and get a grounded, contextual answer that kept the creative flow going.

I wasn't drawing pictures for someone else to implement—I was shaping experience and structure in one breath. Sometimes I'd sketch icons in Illustrator, crafting small, whimsical graphics by hand—the kind of playful details that make interfaces feel human. Then I'd bring them directly into Zed and code them into the layout. Every layer felt connected: hand-drawn charm meeting structured code.

Hand-drawn graphics integrated into the website design
Pretty cute, right? Hover and watch the stickers peel up!

And now that same approach is moving into Giselle's core UI—dashboards, agent flows, even chat interfaces. We're not designing like we used to. We're composing something new, where code, tools, and humans play together in time.

Writing Code, Playing in Harmony

Once I started writing code, something shifted between me and the engineers. I stopped saying “I want this UI to feel like…” and started saying “Let’s make this block position: sticky.” It wasn’t just about picking up the lingo—it was about standing on the same stage, playing the same tune.

I still write code slowly. Half the time I’m not sure it’s even right. But when I can show something I wrote with my own hands, the review gets more specific. Feedback lands deeper. I even remember those debugging spells—the ones you whisper when things go wrong.

That doesn’t mean it all goes smoothly. During the site renewal, I spent days wrestling with a layout issue. An engineer fixed it in minutes. They said, “This structure might work better,” and suddenly I saw the why. Before I coded, that would’ve ended with “Fixed it.” Now it ends with, “Here’s how to try it next time.”

Our whole team brings Giselle’s AI agents into the workflow. We log naming conventions, style guidelines, component specs— and the agents help us keep things consistent without anyone needing to micromanage. It’s a small thing that makes a big difference when you’re designing how humans and AI interact.

Writing code changed my role. I’m no longer just passing designs over the wall—I'm part of the performance. A tiny icon drawn in Illustrator, a small style tweak in a v0 component, a margin fix caught in a review— each adds a note to the score.

And the way we play is changing too. It’s not about who leads and who follows. Designers, engineers, AI—we’re all in the orchestra now. Sometimes I’m at the keys, sometimes AI helps with the rhythm, sometimes an engineer lifts the whole structure.

We listen to each other. We adjust. We keep the tempo. And little by little, the product starts to sing.

That’s Design as Code, Code as Design. It’s how we build—and how we play.

Finding Our Common Language

This shared codebase became our common language. Instead of abstract feedback on a Figma file, conversations became concrete and collaborative. For example, we built our main "Core Function" section by mapping over a clean data structure and composing smaller components like DraggableCard and StickerPeel.

<div className="w-full max-w-[1000px] h-[600px] relative hidden lg:block">
  {coreFunctionCards.map((card) => {
    const cardContent = (
      <>
        <div className="absolute inset-0 rounded-xl bg-gradient-to-b from-white/10 to-white/5 border border-white/15 backdrop-blur-sm" />
        <div className="relative h-full flex flex-col items-center justify-between py-4 px-2">
          <div className="w-full flex-1 flex items-center justify-center">
            <StickerPeel
              imageSrc={card.image}
              width={120}

Having a shared structure like this meant that when an engineer said, "This structure might work better," I could see exactly what they meant in the code. That's not just a fix; it's a lesson that sticks. It's how code stops being a barrier and starts being the bridge.

In many ways, this mirrors what we're trying to achieve with Giselle itself. Just as code became our common language, Giselle aims to create a shared visual language where designers, developers, and AI can collaborate seamlessly. The same principle that dissolved barriers in our team—finding a medium where everyone can contribute meaningfully—is at the heart of Giselle's node-based approach. It's about creating spaces where different forms of intelligence can speak to each other, understand each other, and build together.

The Stage We Build Together

"Design as Code, Code as Design" feels less like a workflow and more like a stage production.

The renewed service site was just the beginning. We didn't choreograph it in Figma—we lit it live, vibe coding in motion, feeling out the weight of layout, the breath of whitespace, the expression of type.

At first, it felt like a solo piece—just me trying to get the steps right. But before long, the whole team found the rhythm. Code became choreography. Reviews flowed like rehearsals. Engineers and AI began reading from the same score.

Code isn't just instruction—it's the score that lifts the curtain. And every time I open Zed with Giselle's agents, I'm reminded: even the most automated stage won't come alive without intention.

If you're curious about how Claude Code enhances the Zed experience, I wrote about it in detail here.

That intention—that pulse behind the scenes—is what makes Design as Code more than a method. It's what makes it real.

I was able to "vibe code" like this because I was in an AI-friendly environment, carefully tuned by our engineers. But I believe this experience shouldn't be a privilege. That's why we want to build agents with Giselle that can support any designer who wants to step into coding, creating a safe space where creativity can flow without fear of breaking things.

The goal is to make this bridge between design and code accessible to everyone, powered by collaborative AI.

Try Giselle Free or Get a Demo

Supercharge your LLM insight journey -- from concept to development launch