Posts tagged as development

  • A small PCB with a single Cherry MX keyswitch on it

    This is a recent prototype.

    It’s a custom PCB that takes a single Cherry MX style keyswitch, with a resistor and an LED positioned to illuminate the keycap, broken out to pins. That’s it.

    It’s part of a larger prototype, that involves buttons and controls and many chips. For a while now I’ve taken to prototyping quite large electronics projects in their full, final form. That means getting a large board made, fully populated with all parts, and then debugging it. It should work first time, but that’s not always the case, and a mistake can mean another costly revision.

    This project has more unknowns in it than normal: new parts (like these keyswitches); new ICs; a UI that is still very much up in the air (and involves keys, knobs, and chording). So I’m prototyping it on a breadboard to begin with.

    Breadboards often mean a lot of dangling jumper wires and bare components. But making small custom modules like the keyswitch module above can make your life a lot easier. In this case, ten small prototype boards to hold a single key were a few pounds in a recent larger order of PCBs. I’ve used hot-swap sockets so I can re-use the switches themselves in later work. The passive parts and pinheader cost pennies.

    But: now I’ve got ten light-up mechanical keys to prototype with, and to reuse in later prototypes.


    The keyswitch board is a particular kind of prototype that I build a lot, whether it’s in hardware or software: a small reusable atom, beyond bare wires, but not of use on its own. Crucially: it’s just for me. It might have utility to somebody else, but that’s by coincidence, not design. As a module, it’s not quite like the development boards in my prototyping drawer from firms like Adafruit and Sparkfun. It’s a more low-level building block.

    I usually call these kind of things test harnesses or jigs. Here’s another jig, perhaps a more traditional use of the term:

    A 3D-printed jig for placing a rubber foot

    This is a small 3D printed jig that assists me in placing an adhesive rubber foot in the correct spacing away from the corner of an object.

    It took a few minutes to design - project the outline of the object, define an offset, extrude upwards, a quick subtraction - and about 15 minutes to print. It does one job, for one particular project, but it made positioning 28 rubber feet quick and repeatable.

    Making a thing is usually about also making the tools to make a thing. Test suites; continuous integration; preview renders; alignment jigs. They’re as much part of the process as making the thing itself, and they are objects that show the growing understanding of the current act of making: you have understood the work well enough to know what tool you need next to make it; to know what tool you need next to think with. Making is thinking.

    The switch jigs helped me understand how many buttons I’d need, what it’d be like if they could light up, whether it’d be useful to have a ‘partially lit’ state. They also helped me do this work without wasting money on permanently soldered switches. The foot jig came out of need: I had placed enough feet by hand to know that a more professional outcome could be achieved in half an hour of CAD and modelling, time that would be somewhat recovered by the quicker, more professional alignment process.

    I love making tools. I particularly love making tools for other people to use and create with. But to only celebrate that kind of toolmaking obscures a more important kind: the ongoing, ephemeral toolmaking that is part of making anything. Making A Tool is not a ‘special’ act; people do it all the time. I think it’s important to celebrate the value of all the tools and jigs and harnesses that are essential to the things we make… and that also are inevitably thrown away or abandoned when the thing they enable comes into the world.

    They’re process artefacts: important on the journey, irrelevant at the destination. I have drawers and project boxes and directories and repositories full of them, for all manner of projects - whether they are made of hardware, or software, or ideas, or words. They seemed like a good subject for some Process Notes.

  • I recently shipped some client work - a small prototyping project - written in Python. Which is surprising, given I would say - if asked - that “I don’t write Python“.

    A lot of people write a lot of Python these days. It’s a common teaching language; it’s a lingua franca for machine learning and data science; it’s used as a scripting language for products I use such as Kicad or Blender. But it’s passed me by. I first wrote Ruby in 2004, which I still love, and that’s served my needs as a general-purpose scripting language, as well as a language for building web applications (with Rails). These days, I’ll also write a lot of Typescript. I don’t really need another scripting language.

    Given that “I don’t write Python“… why did I just ship a project in it, and how did I do that?


    First of all: why Python for this project?

    I needed something that could write to a framebuffer from a command-line, running in an event-driven style. I also needed something that could be used cross-platform, and wouldn’t be too hard for anyone else to pick up. Given this was a prototyping project, ease of manipulation and modification were important, so an interpreted language with no build step would be helpful. As would good library and community support. pygame looked like it would be a very good fit for our project.

    Whilst I wouldn’t admit to writing Python, it turns out I had a fairly strong ambient knowledge of it already. I knew its basic syntax, and was used to its module-style imports via Typescript. I was well aware of its lack of braces and significant whitespace. And someone who loves functional-style code, I was already a big fan of was list comprehensions.

    I paired that ambient knowledge with a couple of core programming skills.

    Firstly : my experience of other event-driven languages and platforms (like Processing, p5js, and openFrameworks) meant I was already familiar with the structure the code would need. An imperative, event-driven structure is going to be pretty similar whether you’re writing in Processing or pygame; I tend to write these with as small a main loop as possible, and then core functions for “set up all the data for this frame” and “render this frame”, broken down as appropriate. You can smell the porting in my code, plus I’m sure I could be more idiomatic, but structure is structure; this meant we began with solid foundations.

    Next: reading documentation. pygame has good documentation, and thanks to its maturity, there’s a lot of online resources for it - not to mention excellent resources for Python itself. That, combined with good experience of usefully parsing error message got us a long way.

    Modern tooling helps a lot:

    • language support in editors/IDEs has gotten really good; the Language Server Protocol means that developer support for interpreted languages is better than it’s ever been. More than just spicy syntax-highlighting, its detailed and comprehsnive support is exactly what you want as an “experienced, but not in this language” developer.
    • What about ChatGPT?“ This is not an article about how I wrote code without knowing how, all thanks to ChatGPT, I’m afraid. But one thing I have begun to occasionally use it for is as a rubberduck; a “Virtual Junior Developer.” “I’m looking for an equivalent to Ruby’s x in Python. Can you explain that to me, knowing that I’m an experienced Ruby developer?“. It usually won’t give me precisely what I’m looking for. But it will give me something in the ballpark that suddenly unblocks me - much like a good pairing partner might. Sometimes, that’s why I need.
    • A rubbderduck I find much more useful is Github Copilot. Again, I don’t think its strength is the “write code for me” functionality. Instead, I most like its ability to provide smart, contextual autocomplete. That’s doubly useful in loosely typed languages, where language servers can be limited in their recommendations in a way that LLMs aren’t limited by. I’m particularly grateful for Copilot as a solo developer; it feels like a pairing partner chipping in with ideas, which, even when they’re not right, at least steer me in a new direction. I’ve found Copilot particularly speeds development up later on in a project. As the codebase gets larger, its intuition becomes more developed.

    The combination of core competencies, modern tooling, and a well-established platform enabled us to not only motor through the initial porting process, but achieve our further goals, with space and time left for polish and improvement within the budget. The final codebase met the client’s needs: it worked well cross-platform, was straightforward (thanks to virtualenv) to get up and running on a colleague’s development computer, and is a good foundation for future work.


    Programming work - I hesitate to say “creative programming” because all programming is creative - is about much more than just ‘knowing a language’, and this project was a great example of that.

    Much more important is knowing how to learn new languages (and how you best learn new things); understanding patterns common to styles of language; maintaining good code hygiene and great documentation; and finding ways to steer yourself in the right direction - whether that’s a partner to pair with, the right developer tool, a good online resource, or even a modern application of AI.

    My evaluation at the beginning of the project had been validated. As I’d suspected, actively choosing to work in a new-to-me platform was not a risk. It turned out to be exactly the right tool for the job - a prototype where speed of iteration and flexibility were highly valued.

    That evaluation comes down to something I often describe as a sense of smell; a combination of expertise, personal taste, and ‘vibes’. Perhaps it’s easier just to call that experience. It turns out that “twenty years of writing software” beats the fact that almost none of it has been Python.

    We wrapped this small project last week, and I enjoyed my exposure to Python as a more experienced developer. I also valued being reminded me of what experience feels like, and what it enables: good judgment, flexibility, and focusing on the project’s outcomes, rather than getting lost in implementation.

  • 2023 was frustratingly fallow, despite all best efforts. Needless to say, not just for me - the technology market has seen lay-offs and funding cutbacks and everything has been squeezed. But after a quiet few months, the end of 2023 got very busy, and there’s been a few different projects going on that I wanted to acknowledge. It looks like these will largely be drawing to a close in early 2024, so I’ll be putting feelers out around February. I reckon. In the meantime, several things going on to close out the year, all at various stages:

    Lunar Design Project

    After working on the LED interaction test harness for Lunar, I kicked off another slightly larger project with them in the late autumn. It’s a little more of an exploratory design project - looking at ways of representing live data - and that’s going to roll into early 2024. More to say when we have something to show - but for now it’s a real sweetspot for me of code, data, design, and sound.

    Web development project “C”

    More work in progress here: a contract working on a existing product to deliver some features and integrations for early 2024. Returning to the Ruby landscape for a bit, with a great little team, and a nice solid codebase to build on. Lots of nitty-gritty around integrating with other platforms’ APIs. This is likely to wrap up in early 2024.

    This and the Lunar project were primary focuses for November and December 2023.

    Nothing Prototyping Project

    Kicking off in December, and running into January 2024: a small prototyping project with the folks at Nothing.

    AI Clock

    The AI Clock firmware running on its production hardware.

    A short piece of work for Matt Webb to get the AI Clock firmware I worked on in the summer up and running on the production hardware platform. The nuances of individual e-ink devices and drivers made for the bulk of the work here. Matt shared the above image of the code running on his hardware at the end of the year; still after all these years of doing this sort of thing, it’s always satisfying to see somebody else pushing your code live successfully.


    Four projects made the end of 2023 a real sprint to the finish; the winter break was very welcome. These projects should be coming into land in the coming weeks, which means it’s time start looking at what 2024 really looks like come February.