DEV Community

ggwork
ggwork

Posted on

Building a Geometry Calculator: What AI Got Right, Wrong, and Everything In Between

While working on a collection of browser-based developer tools, I hit an unexpected wall. I needed a geometry calculator — not for myself, mind you, but as one of those "everyone expects it to exist" tools that round out a utility suite. You know the drill: area, perimeter, volume, the usual suspects.

The problem? My requirements were deceptively simple. Eight shapes. Dynamic inputs. SVG diagrams. i18n support. Dark mode. I figured this would take an afternoon, tops.

Spoiler: it took three sessions with AI assistance, and the journey taught me more about AI-assisted development than any "hello world" tutorial ever could.

The "Simple" Requirements That Weren't

Let me break down what I thought would be straightforward:

  • 8 shapes: circle, triangle, rectangle, trapezoid, parallelogram, sphere, cylinder, cone
  • Dynamic input fields that change based on shape selection
  • SVG diagrams for each shape
  • Bilingual support (Chinese/English)
  • Dark mode

Sounds manageable, right? The first prompt I gave to the AI was something like:

"Build a geometry calculator with 8 shapes, dynamic inputs, SVG diagrams, i18n, and dark mode. Pure vanilla JS."

The AI generated a working version in about 30 seconds. It looked great. It functioned. And then I started testing edge cases.

Where the AI Nailed It

The initial structure was solid. The AI handled the shape selection logic cleanly, and the SVG diagrams were surprisingly good. Here's a snippet of the shape data structure it created:

const SHAPES = {
  circle: { inputs: ['r'], svg: 'circleSVG' },
  triangle: { inputs: ['b', 'h', 'a', 'c'], svg: 'triangleSVG' },
  rectangle: { inputs: ['w', 'h'], svg: 'rectSVG' },
  // ... more shapes
};
Enter fullscreen mode Exit fullscreen mode

This data-driven approach meant adding a new shape was just adding an entry — not rewriting logic. Smart architecture from the start.

The formula implementation was also spot-on. For the circle:

function circleFormulas(r) {
  return {
    area: Math.PI * r * r,
    circumference: 2 * Math.PI * r
  };
}
Enter fullscreen mode Exit fullscreen mode

Clean. Correct. No surprises.

Where It All Went Wrong

Here's where things got interesting. The first real bug appeared when I tested the triangle with three sides (SSS case). The AI had implemented Heron's formula correctly for the area, but the perimeter calculation was... well, it was just the sum of sides. Which is correct, but the AI forgot to handle the case where the triangle inequality is violated.

// AI's initial version
function triangleFormulas(a, b, c) {
  const s = (a + b + c) / 2;
  const area = Math.sqrt(s * (s - a) * (s - b) * (s - c));
  return { area, perimeter: a + b + c };
}
Enter fullscreen mode Exit fullscreen mode

Try putting in sides 1, 1, and 10. You get NaN for the area, and no warning. A user would be completely confused.

The fix required checking the triangle inequality before computing:

function isValidTriangle(a, b, c) {
  return a + b > c && a + c > b && b + c > a;
}
Enter fullscreen mode Exit fullscreen mode

This was my first "aha" moment with AI-assisted development: the AI writes beautiful code for happy paths, but edge cases are where you earn your keep as a developer.

The Dark Mode Saga

I mentioned dark mode in my requirements. The AI implemented it using CSS variables with a prefers-color-scheme media query. Perfect approach, right?

@media (prefers-color-scheme: dark) {
  :root {
    --bg: #1a1a2e;
    --text: #e2e8f0;
    /* ... */
  }
}
Enter fullscreen mode Exit fullscreen mode

But here's what the AI missed: the SVG diagrams. They were hardcoded with dark colors for strokes and labels. In dark mode, they became invisible against the dark background.

"Classic 'works on my machine' situation," I muttered, adjusting the SVG colors to use CSS variables:

<svg>
  <circle cx="50" cy="50" r="40" 
          stroke="var(--text)" fill="none" stroke-width="2"/>
  <text x="50" y="85" fill="var(--text-secondary)">r</text>
</svg>
Enter fullscreen mode Exit fullscreen mode

The AI learned from this and started using CSS variables in subsequent SVG generations. It was like watching a junior developer grow in real-time.

The Input Validation Trap

Another subtle issue: the AI allowed negative numbers and zero in the input fields. A circle with radius -5 shouldn't be a thing, but the AI was happy to compute Math.PI * (-5) * (-5) = 78.54. Technically correct, semantically wrong.

I had to add validation that the AI kept getting subtly wrong:

function validateInput(value, label) {
  const num = parseFloat(value);
  if (isNaN(num) || num <= 0) {
    throw new Error(`${label} must be a positive number`);
  }
  return num;
}
Enter fullscreen mode Exit fullscreen mode

The AI initially used Number(value) instead of parseFloat, which meant empty strings became 0 instead of NaN. That's a subtle bug that would've frustrated users.

The i18n Architecture

For the bilingual support, the AI suggested a translation object pattern that turned out to be elegant:

const i18n = {
  zh: {
    circle: '圆形',
    area: '面积',
    // ...
  },
  en: {
    circle: 'Circle',
    area: 'Area',
    // ...
  }
};
Enter fullscreen mode Exit fullscreen mode

But the first version had a critical flaw: it only translated the UI labels, not the formula display or the SVG text labels. When you switched languages, you'd get a Chinese UI with English formulas. Not ideal.

The fix was to make the formula generation function language-aware:

function getFormula(shape, lang) {
  const symbols = i18n[lang].symbols;
  return `${symbols.area} = π${symbols.radius}²`;
}
Enter fullscreen mode Exit fullscreen mode

This was the point where I realized: AI is great at scaffolding, but you need to think through the user experience yourself.

The Performance Question

You might wonder why I didn't just use an existing library or online calculator. Trust me, I considered it. But the requirements were specific:

  1. Pure frontend (no server calls)
  2. No external dependencies
  3. Works offline
  4. Fast initial load

The AI suggested using Math.PI directly instead of hardcoding 3.14159, which was correct. It also recommended rounding to 4 decimal places to avoid floating-point weirdness:

const round = (num) => Math.round(num * 10000) / 10000;
Enter fullscreen mode Exit fullscreen mode

This handles the classic 0.1 + 0.2 !== 0.3 problem gracefully.

What Actually Worked

The AI-assisted approach really shined in these areas:

  1. Rapid prototyping: Got a working version in minutes, not hours
  2. Consistent patterns: The AI maintained consistent naming conventions and code style throughout
  3. SVG generation: Creating 8 different SVG diagrams was tedious, but the AI handled it well
  4. CSS architecture: The variable-based theming was solid from the start

What I Had to Do Myself

  1. Edge case thinking: AI doesn't naturally consider "what if the user enters garbage?"
  2. UX decisions: When to show errors vs. auto-correct, how to handle empty states
  3. Cross-browser testing: AI can't tell you that Firefox handles SVGs slightly differently
  4. Accessibility: Adding proper ARIA labels and keyboard navigation

The Collaborative Loop

The most effective workflow I found was iterative:

  1. Describe the feature in plain English
  2. Get AI-generated code
  3. Test with edge cases
  4. Point out specific bugs
  5. AI fixes them
  6. Repeat

For example, when I found the triangle inequality issue, I said:

"The triangle area calculation returns NaN for invalid triangles. Add validation and show a user-friendly error message."

The AI not only fixed the calculation but also added the error message infrastructure. It was learning from my feedback.

Lessons Learned

AI is a fantastic junior developer. It's fast, consistent, and never gets tired. But it needs supervision. It'll happily implement a feature with subtle bugs that only show up in edge cases.

The prompt matters more than the model. Being specific about requirements — "show the formula alongside the result," "use CSS variables for theming" — made a huge difference in output quality.

You still need to understand the math. The AI can write formulas, but you need to verify them. I caught a bug where the cylinder surface area formula was 2πr(r+h) instead of 2πr² + 2πrh. They're mathematically equivalent, but the AI's version was harder to read and explain to users.

The Final Result

After three sessions of back-and-forth, I had a working tool. It's not perfect — nothing is — but it handles all the edge cases I could think of, supports both languages properly, and looks decent in both light and dark modes.

The whole process made me appreciate the collaborative nature of AI-assisted development. It's not about replacing the developer; it's about amplifying their capabilities. The AI handled the tedious parts (SVG diagrams, repetitive code structure) while I focused on the parts that require human judgment (UX decisions, edge case handling, accessibility).

During this process, I built a small browser-based tool to make this workflow easier. You can check it out if you're curious about geometry calculators or want to see the final result in action.

Final Thoughts

If you're thinking about using AI for your next project, here's my advice: treat it like a pair programmer who's read every Stack Overflow answer but has never shipped a product. It's brilliant at patterns and syntax, but it needs your experience to know what "done" actually looks like.

The geometry calculator taught me that AI-assisted development isn't about writing less code — it's about thinking more clearly about what you want that code to do. And sometimes, the most valuable output isn't the code itself, but the questions it forces you to ask about your own requirements.


Tags: javascript, webdev, ai, tools, productivity

Top comments (0)