Notes

Thoughts on programming, games, and whatever else.

  • GrobPaint

    2026-03-15

    I released GrobPaint, a lightweight image editor that sits somewhere between MS Paint and Paint.NET. It's multiplatform by default, which was the main motivation. I've been wanting a simple Paint.NET replacement on macOS for years and nothing quite fit. I always found GIMP's UI to be clunky and Krita to be weird, most likely because I've grown so accustomed to Paint.NET. I've only ever heard good things about Asesprite, but too tailored to pixel art for me. No knock on any of those projects! Probably just me being overly particular.

    Anyway, now that I'm addicted to Claude Code, I thought it probably wouldn't be too hard to just roll my own.

    GrobPaint

    It's built with vanilla JS and a small Python backend. No frameworks, no Electron. About 5,000 lines of code total. Layers, blend modes, magic wand, lasso, the usual stuff you'd expect. Try it out in your browser!

    I posted it on Hacker News and it got some nice traction. The GitHub repo is already over 100 stars, which is cool and unexpected. My Simple Markdown Editor also got more traction than I expected on HN (I should really post more!)

    Actively developing this one. If you have feature requests, open an issue on GitHub.

  • I recently prototyped an idea of making an interactive version of Lisp using visual blocks, inspired by Scratch (which is how I originally learned programming!).

    There are two types of blocks - lists and atoms. The lists automatically lay themselves out either horizontally or vertically depending on how nested they are.

    Lisp visualization

    You can right-click on blocks to execute them, and defining variables makes them show up as blocks in the environment - making the environment itself editable and interactive.

    Executing blocks

    Here you can see me defining a variable and a function, and then using the function to update the variable in the environment.

    Executing blocks

    This project isn't live yet because I'm still working out the bugs. Hopefully soon!

  • Local LLM Optimism

    2025-09-14

    I don't want to make costly API calls to a supercomputer, I want to run the LLM on my own machine, have it be efficient, and have it be smart, too.

    Things appear to be generally moving in this direction. The new local LLMs released by OpenAI (the GPT-OSS series) are pretty good locally, even the 20B model is reasonably smart and runs well on my M4 MacBook Pro that I bought earlier this year. The time to first token still isn't perfect, but it's reasonable and the intelligence of the model is reasonable too. In my experience it can handle some non-trivial programming tasks such as writing custom MDPs in Julia given some reference documents.

    My hunch is that, because the demand is there for local LLMs, we will get more tech moving in this direction. To this point I'll suggest Apple's upcoming M5 chip's upgraded neural engine as evidence.

    I am optimistic that we can avoid the future where a few megacorps control the only AIs in town.

  • When programming, I care about iteration time. A lot.

    It affects my choice of tech stack dramatically. Maybe more than most other single consideration besides ecosystem. And, unlike ecosystem, I don't think enough developers talk about iteration time.

    Iteration time is the time it takes for you to write a change to a line of code and see that change reflected in whatever you're building. When this time is low, I can flow as a developer. Stay in the flow state, never leave context. Put on some good coding music (drum and bass, anyone?) and go for hours pounding coffee. :)

    When build times become a consideration, this all flies out the window. Make a change, run a compile, oops now I'm browsing Hacker News or Tiktok. There goes 15 minutes! Oh wait, what was I doing again? So much time wasted, so many context changes! Productivity tanks by like 50%.

    This is part of the reason why I love scripting languages so much, or Julia with its REPL-driven development. I much prefer dealing with runtime errors or mucking up some typing issue than breaking my flow state.

    Maybe you're the same way. Or maybe you just don't know it yet.