Supper Club × Steve Ruiz Building a Drawing App
29 Apr 2026 · 56 min
In this episode of the Syntax Supper Club, hosts Scott Tolinski and Wes Bos interview designer‑turned‑developer Steve Ruiz about his open‑source drawing tool TLDraw (formerly TealDraw). Steve walks through the origins of the project, describing how a six‑month research effort into variable‑width digital ink led to the Perfect Freehand algorithm and the Globs prototype. He explains why he chose DOM/SVG over HTML Canvas, how the browser’s native paint cycle provides free rendering optimizations, and how he built a smooth, high‑performance UI using React, CSS transforms for zoom/camera, and a custom state‑machine architecture wrapped around a Zustand store. The conversation covers persistence (IndexedDB, local .tldr JSON files, VS Code extension), real‑time collaboration via Liveblocks, mobile support using pointer events and the React‑Use‑Gesture library, and PWA considerations. Steve also shares his personal journey, learning resources (Hacker News, One Lone Coder, game‑dev channels), tooling preferences (MacBook Pro, VS Code Monokai Pro), and advice for newcomers. The episode ends with “supper‑club” rapid‑fire questions and a plug for TLDraw as a developer platform (tldraw.dev).
Chapters
I sure hope you're hungry! Hoo, I'm starvin'! Wash those hands, pull up a chair, and secure that feed bag! Because it's time to listen to Scott Talinsky and Wes Boss attempt to use human language to converse with and pick the brains of other developers! I thought there was gonna be food! So buckle up and grab that oh shit handle, because this ride is going to get wild! This is The Syntax Supper Club.
Welcome to Syntax. On this Syntax Supper Club, we're going to be talking to Steve Ruiz all about Google Sponsors and TL Draw, which is a really, really interesting application. A little tiny— it was a tiny little— or what is it? Tiny drawing app?
Tiny little drawing app is a little bit of a retcon. I could tell a story about how the name got started, but yeah.
Yeah, we'll have to get into that. My name is Scott Talinsky. I'm a developer from Denver and with me as always is Wes Bos. How's it going, Wes?
Hey, doing pretty good. Pretty good. Excited to talk about, uh, literally everything here and just playing with this app. I'm like, this is really cool. I have so many questions of how this works and what decisions you made. So yeah. Yeah.
Pretty good. Yeah. So welcome, Steve Ruiz.
Uh, we're happy to have you Longtime fan of the pod. I'm sitting in my nice air-conditioned office on the hottest day of the year in London. So yeah, it's not bad at all.
It's been super hot here too. We've just been baking, baking out here in the 100 degrees. Wes, you're probably pretty psyched to be up there in Canada.
Yeah, well, Canada gets really hot too. It's been like 35. Hold on, let me convert 35. Yeah.
What?
Yeah, 35. I thought that's cold.
Yeah.
Celsius to Fahrenheit.
Let's see. 95 Fahrenheit, so certainly not 100 just yet. But yeah, Canada, that's one thing people always think Canada's cold, like all the time. It's like, no, it's like wicked hot in the, in the summer. And then it gets like cold for like February. And then it's like snowy for a couple more months past that. I guess it depends where in Canada you are.
People think that about Denver too. It's really funny. We were in line at Legoland. Some lady from Vegas was like talking to us and she was like, oh, it's really cold in Denver. Like, no, it's like 100 right now. It's, we get a lot of sun. She's like, oh, it's really humid too, right? I'm like, no, it's, it's like dry desert climate. Like just like totally wrong about everything. We're, we're like really far, we're further south than Michigan or anything like that. So I don't know why people think it's so cold.
Maybe just the mountains, but yeah, we get the wicked humidity here, which is like always like people always say, oh yeah, it's, it's 32, but it feels like 40. And then you always have to like convert for people. Cause you'd be like, it actually feels, feels like hotter than it actually is.
I promise you're in Hamilton, right?
Yeah, yeah, yeah.
I've actually been there once. Uh, oh, I, I'm originally from Chicago. Now, now I live in London, but originally from Chicago, so I think we have kind of like similar weather.
Oh yeah, yeah, definitely brutal, very humid. Yeah, yeah, exactly. And Chicago gets brutal winters too, right?
Yeah, it does. Yeah, that's both worlds.
Yeah.
All right, well, let's, uh, let's get in into the app there, or get into it, or do you want to give us like— let's give you— give us a quick rundown of who you are, Steve, and yeah, for sure, for sure.
So my name is Steve. I am kind of a designer turned developer who I made my— I spent my career kind of doing prototyping and doing these interactions and the trickier parts of design that just you had to build something in order to figure out how it should work. And got a little bit into open source during the pandemic. And then one of my projects, TealDraw, um, ended up being pretty popular. So now I get to work on that full-time. So it's been kind of a journey, but, uh, yeah, still, still getting to code, still getting to design, um, and trying to pack as much little micro-interaction goodness into, uh, TealDraw as I can.
Yeah. Micro-interaction. Uh, that's kind of the name of the game in this thing, cuz this, uh, has a lot of, uh, neat little interactions, neat little general general touches, I think. So we'll be getting a bit into the tech of that as well.
For sure.
This episode is sponsored, by the way, by Gatsby. We'll be talking a little bit more about Gatsby through the course of this episode. Okay, so let's get into it. Do we want to kick it off with TL;DRAW? Um, I, I think that'd be a good place to start considering it's so— yeah, I think a lot of people will find a lot of inspiration in this thing. So if you're out there and you're, you're Wondering what is this thing? Go to tldraw.com and it's essentially a drawing canvas and it, it's really super neat. There's a lot of really cool things about it, but just start toying around with it, play around with it, dive into the source. Look at this thing. If you, especially if you're in front of a computer, because it is essentially a drawing canvas, a vectorized drawing canvas built in React. So. You might just be kind of shocked at how cool this thing is. I want to, I want to know a little bit about the inspiration for building TL;DRAW. Like what made you decide, hey, I'm going to, I'm going to work on this, this problem that seemingly seems very difficult in my mind. Yeah, for sure. Okay.
So there were a couple of things that kind of converged in TL;DRAW. One, uh, was I had been working on this algorithm for, kind of digital ink, like a variable width line. So if you're in SVG, for example, right, and you wanna make a path or a line, you can pick the stroke width, but you can't make that stroke width change over time. And so if you're like used to maybe drawing on an iPad or something with a stylus, you know, like if you push hard, then the line gets bigger. If you don't push as hard, the line gets smaller. And I ended up working for like 6 months on this problem for SVG, for anything really. Like, how do you make a variable-width line that's like sort of digital ink? And mostly did it on Twitter. Kind of shared my journey in the form of like little 8-second GIFs. So it's figuring out this algorithm. And in the end, it actually turned out pretty well. So I had this pretty cool algorithm that I could feed any points into and it would give me back what looked like an ink-drawn line that kind of wrapped around those points. I, in the process, in the process of working on that project, I ended up working on a project called Globs, which is at globs.design. And definitely check this out. It's unlike any kind of design tool you've ever used because the only thing you have to work with are these these weird primitives called globs, which are kind of two circles that are connected. And you could move each one of those circles around and the kind of the curves between them would, will, will always kind of smoothly connect those two circles. And I was pretty sure that I could use these globs to create the pressure-sensitive line. I turned out not to be able to, to do that. The algorithm doesn't use globs. But along the way, I made this entire design tool, essentially, like this kind of canvas, all in SVG, SVG and React for editing these globs. And so, you know, early 2021, I would say, I had this ink, I had gone through and kind of figured out a lot of the interactions involved in like a canvas-based tool, like a design tool canvas. And I also, um, had figured out a lot of like the, the state machines for those things. So like what, what does the state chart for a, for a kind of an application like that look like? Um, I was invited to integrate MyInk into another tool called Excalidraw, uh, which is a similar like drawing diagramming tool for, for developers especially. And so if you go on excalidraw.com, which is an amazing also open source project, My digital ink is used there. So, I was working in their codebase and I was thinking, you know, this is kind of like— this is really cool. I bet you could just do this, A, with only React, React and SVG. And B, I bet I could do this using my own kind of ink. So, I started working on that, like a new design tool that used a lot of what I learned building Globs, used the digital ink that I had that I could just, you know, create shapes and etc., like rectangles and triangles and circles using, using this algorithm. And then, yeah, just kind of, kind of put it together and see if I can make a little drawing tool, a little kind of whiteboarding tool. And it turned out to work pretty well. And I also kind of gained a lot more confidence in that, like, you could build this type of what I would normally consider like you would use HTML canvas to build this type of canvas. Yeah, yeah. But the more I used just regular DOM, like, you know, divs and images and stuff, I was like, actually, this is pretty fast. Like, browsers these days can actually handle this. So, I just kept going with it. And once you have a canvas that can put React components, arbitrary React components like on the canvas and move them around and reorder them, then suddenly there's a lot of like really interesting opportunities to kind of develop with that. Yeah. So I worked on it, started doing it full-time in July of 2021 and released it in November 2021. So just a couple of months full-time on it. I open-sourced the entire thing. So the whole website, the source code, for the whole thing is online, github.com/tealldraw/tealldraw. And yeah, suddenly people started contributing, which was great. I think it went to like the top of Hacker News, which was amazing at the time. And what was fun was like other teams started building with this and saying like, ooh, cool, like a canvas that you could put React components on the canvas. Like, you know, we could use that with our app or we could use that, you know. And so we started getting a lot of cool integrations, um, and a lot of like interesting kind of directions that people took it. Um, and continue to take it, I suppose.
Yeah. It's pretty amazing. Especially if you look at it, like you mentioned a canvas, like the first thing that I thought of when I saw it was, oh, this is probably done in, in canvas only because the types of tools that I've seen like this are typically done in canvas. And so when you, when you get into it and you find that it's DOM elements, SVG. It's really pretty neat. So, what was the main reason you said I would prefer not to do this in Canvas?
[Speaker:JASON] It was actually another team that was working with it. Originally, it was just one big SVG. And they were like, you know, we want to put like more complex things. Like we want to put calendars or to-do lists or sticky notes and such on the Canvas. And like How do we do that? And, you know, you can build those things in HTML Canvas. It's just a super hassle. Like, all the things that you get when you're building for the web, like text wrapping or multi-line text, you know, all of that's out the window. You have to reimplement it from basically from scratch. Yeah, I just kind of like ran it as an experiment. I'm like, all right, well, what if instead of using SVG elements and everything inside of SVG, like what if we just switched to just full, you know, divs and stuff, like regular HTML, regular DOM. And it turned out to work fine. So, an image like maybe like a rectangle rather than— originally this was like a, you know, SVG path inside of a group. That was inside of the one big SVG that was the whole page. Yeah. Now the— that same shape would be still an SVG, but it's its own SVG shape inside of a div that we're kind of positioning on the canvas that way. Uh, and then so suddenly we were still able to make our shapes, our kind of drawn shapes, but this team that was building with TealDraw was also able to throw together like a timer component that would have taken months just to do and test the UI. Um, and they could do it like in an afternoon with, with their same web devs and with no special graphics engineering, you know, needed. And that, that's a game changer.
I think, um, that, that's always been the, like the hangup for me with canvas is that like, it's like Microsoft Paint. As soon as you put the pixels on the thing, you can't go get them and change the color. You can't select them. Uh, and, and you got to like, essentially you have to just like maintain a huge array of every single thing that was done. And if you want to change something about it, then you got to like redraw the entire thing. And that's really frustrating. And then, like you said, like in the past, I've wanted to like overlay some text or something like that. It's such a pain in the butt to do.
So it's amazing. Yeah. In Canvas, I remember just doing a simple animation and just being like, wait, I have to clear the animation. Each time to read and redraw it based on the new— like, I just remember being very like, oh wait, so you're not supposed to do this without other tools to help you do this because it's so complex.
Yeah. I mean, rendering in, in general is like a really hard problem, but what, what's fun is that the browser still has to solve that problem. You know, like the browser is— we're looking at essentially an image, right? Like there's a, there's a paint cycle, right? The, the browser is painting the screen and it needs to paint only the parts that have changed and it needs to paint certain things on different textures and then composite them together and flatten them together. All of those optimizations that the browser does for a normal HTML page, yeah, with Canvas or with WebGL or something, you have to just do those same things yourself. And so, the good news is that the browser is pretty good already at doing those type of optimizations, at making sure that it paints only the parts that need painting and stuff. Um, and so yeah, you get, you get that all for free. I didn't even know how much we got for free until I started on this project. It was pretty fun.
It was pretty sweet. TLDraw is incredibly smooth. Uh, I mean, it's not— granted, you're, you're doing a lot of, probably doing a lot of math on, on each drag of anything, right? But in terms of, um, yeah, it's just math. Uh, in terms of just overall UI speed, the thing doesn't even hiccup. For a second. It's pretty, pretty slick.
I spent a lot of time on that. I mean, you can make a joke. You can definitely, it's not, if you put it next to something like Figma, right? Figma's, its renderer, I hate that word renderer, is super fast and like ridiculously optimized. And it's, it's, it's never going to be as working with just HTML and CSS is never going to be that fast. But then again, for diagramming, for drawing, for most things, uh, it's fine. And I've put a lot of effort into making sure that even if the whole document has a lot of stuff on there, the thing that you're doing, like if you're drawing a line, if you're drawing an arrow, that part of it is going to go fast. So you won't, won't notice the kind of the bulk of the document until you try and maybe like start resizing like 200 boxes or something. Yeah. And then your computer is going to be like, oh yeah, give me a second. I'm doing this, all this math and JavaScript, like, got to give me a second.
Yeah. That's, uh, so I have a question about, um, like the first thing that I did when I tried it, I was like, this is smooth. Cause I've done a lot of canvas before and literally the canvas will just follow your thing and you can make it like a, you can make an arced, um, like you can make your brushstroke circle and it's a little bit better, but like, this is so smooth and it's because of the algorithm you're, you're taking like that you've written. So like, like how do you make an algorithm? Like where do you even start? Do you have a mathematics background or are you just like, are you really good with the pen tool?
My background, believe it or not, I mean, maybe it makes sense. The next best thing to having a math background is my background is in fine art, in painting and drawing. So, I had to learn a lot of entire topics of math, linear algebra and vector math and all that in order to figure this out. But, as I'm sure you know, just any type of developer, you just pick a problem and then learn what you need to do in order to make that problem not a problem anymore. And I, uh, yeah, just kind of learned it that way. But, um, the— I think the origins of that pen tool, uh, it's called Perfect Freehand, by the way, and this is also open source. It's on, uh, it's on GitHub. You can use it in your own project. It's used, you know, it's used in a bunch of places. Um, if you are a commercial project and you want to use this, you should sponsor me on GitHub, but we'll come back to that. Uh, But yeah, if you can think of it almost like a, like a racetrack, right? You have points along the middle of the racetrack, and then, you know, to the left of each point you have like two more, you know, one point, and then to the right of that point you have another point. And if you want the racetrack to get wider, then you just make the left point go a little bit further and the right point go a little bit further. And if you want it to get narrower, then you bring those left points and right points kind of closer together. And so that's the simple idea is you just take all the input points and you kind of create new points that surround them to the left and the right. And then you solve about like 30 edge cases, all having to do with like sharp corners and, you know, scribbles, like when someone's just moving their pencil, pen back and forth. Um, and then the idea of like, if you are using an iPad Pencil or something that will report real pressure, then we'll use that real pressure, right? So push hard and it'll get wider, push, you know, don't push much and it'll get thinner. But if you're just on your, uh, computer using a mouse or trackpad or, you know, like your finger on a, on an iPhone, um, we'll simulate that pressure based on how fast you're going. Okay. So if you go, go slow, then it'll get kind of like a fatter line. And if you go, you know, fast, then it'll, it'll get thinner. Uh, and there's, if you do go to the repo for Perfect Freehand, there's like a playground, a specific kind of website, demo website where you can adjust all those knobs and kind of like play with the thinning and the different options for that algorithm in order to kind of dial it into, uh, to different sort of aesthetics. Um, but yeah, there's a, there's a lot, a lot to it, but the, the algo itself is not super long. It's just, uh, it's like I said, it's a simple idea with a lot of edge cases.
I'm sure that's a big, big component of it.
So I was curious if you were using the pressure, um, values, because if people don't know, in I believe it's pointer events, there is a pressure value that will come through on devices that it. So did you— that was one of my questions I had written down before I even started this thing. Do you use touch events? Do you use mouse events? Or do you use pointer events?
Pointer events. Pretty much exclusively. I mean, pretty much all the browsers now implement pointer events. They don't do it exactly the same, but I feel like that spec is better adhered to than some of the other ones involved in like kind of touch events and stuff. So yeah, like you say, most devices, like the general rule, the rule that it should be is that if you, your device does not support pointer events, then you get a pressure value of 0.5. If it does, then you get something else. That is not always true. For example, I think like Wacom tablets, Um, they do report pressure, but they have like a, a type of a mouse instead of like a type of a pen. Oh man. Whereas like your iPad pen will be like a type of a pen. Okay. Um, so you, you can't, you can't rely on the type too much. And I think Safari has some, some cursed thing where it'll report like 0 pressure instead of 0.5 pressure. So, uh, but you know, they're working on it. So yeah, if you can get it and if you can reliably kind of identify, okay, this, this thing has pressure that's changing over time, then that's probably, that's probably a, you know, device that, that reports pressure. Um, and if you don't have that, then you can simulate it. You can use, uh, like an acceleration, um, math in order to, to kind of do it that way.
Okay, so like the faster you go, the thinner the line gets?
Yeah, it's like the more the if you can imagine the distance between each point, um, so A and B are close together, B and C are a little further apart, and then C and D are a little further apart more, then you sort of adjust the pressure based on like in which direction is it changing and how much is it changing. Oh my God, like are they, are they getting further apart or closer together? Um, and then you can, you can do it like that, but Wow. Yeah. There's also a lot of like, uh, noise when people are drawing with like a pen or their finger. Like the line itself, it's actually kind of like, the line itself is kind of like all over the place. Yeah. Um, so we have to, we kind of have to smooth it. Do you smooth it after the fact? Is that— No. The, the big constraint here with Perfect Freehand is that unlike something like using the pen tool in, in most vector drawing apps, uh, Well, in most vector drawing apps, as you draw, you get this kind of like bad-looking version of the line. Uh, and then when you finish drawing, it simplifies that line and smooths it and everything like that. Um, my constraint with Perfect Freehand was that the line should always look the way that it's gonna look. Nice. Um, and so it does, like, it does some simplification as you draw. but it should feel like you're actually like laying down ink or doing it. There isn't this like two-phase thing. It's just always there. Oh yeah. And yeah, again, a lot of, a lot of time went into making sure that we could do that, um, in a way that, that was like consistent so that like the, the start of the line didn't change while you were like, you know, drawing the, the other side of the line. Um, so it's like the decisions it makes about how to simplify are like consistent, like they won't change in the future.
Uh, even if you add new points, I think that's really important because I mean, too many times you do, you, you do your drawing, especially in some of these ones that, that Post Completes it and you think, okay, uh, this is, this is how I wanted it to look. And then like the moment you lift up your pen, it snaps to something that's smoother, more simplified, oftentimes worse or different. But I do understand the importance of needing to smooth it all because obviously that noise isn't going to be helpful for you. I'm wondering about the state management of this thing. We all know React apps, they got state, right? We got a lot of different state management tools. You mentioned that you utilize state machines earlier on in the episode. So, I take it you're using state machines here, and if so, what's your solution for state management in general for something like this? Because I would imagine state is part of what makes this thing as performant as it is, but also as able to be as complex as it is.
Yeah, yeah, precisely. Um, so I've kind of gone through a couple of different solutions. Originally I was using a library that I also— like my own state chart library similar to XState. It's called State Designer. You can look at it, probably don't use it, but it's a— I built it for a kind of like a UI around state using state charts and such. Probably an entirely different episode where we could chat about that. I then, I think the actual state management that I'm using in TealDraw, the store, it's like a Zustand store. But I'm kind of wrapping around it. There's a couple of concepts, like I call it a session, but it's really just, it's a state. It's like a thing that begins and ends. So for example, you start dragging a shape around, right? You've drawn a shape. Now you've started moving it around. We would call that like a translating session. And once this kicks off, only a couple of things can happen. Either it can update, like, okay, I'm moving the mouse now, I'm updating, right, in this session, or it can be canceled. So maybe I press Escape and I say, you know what, never mind, put that thing back where it was, or I complete it. So maybe I stop clicking. And now we've ended the session. We've created something like a new entry in the undo, redo, the history. And we're okay to start a new session. And the premise there is that, like, you can only have one session at a time. And if you're in a session, then you know what, what can happen next. And there are only a few things can be— can actually happen and everything else gets ignored because, hey, I'm in a session. So this is a lot like in a state machine, right? Like you're you're in an idle state. Now I'm in the translating state. And, you know, there's only a couple of events that are going to kick me out of translating and let me go back to idle or let me go back to a different state. In the— I'm kind of in the middle of a rewrite of TealDraw. And in that case, things are a lot more explicit. Like it is a tree of states. Where each kind of state has children, like maybe selecting has like, you know, am I pointing a shape or am I clicking on a shape or am I clicking on the canvas, etc. And while each state can have an active child or must have an active child if it has children, you know, only one of its children are active at a time. So it's kind of like nested state machines very much. Like if you've ever talked to David from Stately or XState, the same concept there is that you have like a, you know, one state machine is great, but you know what's even better is a whole tree of state machines that nest inside of each other. What it ends up being though is it's like while I'm in this particular part of the state chart, right? The state of where I'm like rotating a shape, but I'm also holding like the Alt key. So, or whatever that is. Once I'm in that state, I know that only a couple of things matter, right? Only the pointer position changing matters. Only the, you know, whether they lift the Alt key or not matters. And so you can write pretty tight code for just that part of the state rather than, uh, having like an incredible pile of like if-else statements, you know, like if, uh, I started dragging and if I have things selected and if I'm holding Shift key, then do this and unless this other thing. So, you're able to kind of like focus on the parts of the— like the interactions that actually matter or that are going to change something. And then you can ignore everything else. So, yeah. Again, kind of like a bigger topic of managing state with state machines, but you have to with something like this. Because when you think about it, in a drawing app, you only have like two interactions. You know, like people are just going to be clicking and then they're going to be dragging. And like, that's pretty much it. Maybe they're going to be scrolling their mouse wheel, but like those clicking and dragging can matter, like produce such different results depending on like what, what just happened before or what, you know, um, what thing you have selected and all that. So the only way to manage it is to like start carving it up into different states.
Yeah. I think a good concept or a good takeaway from even even what you had to say there was just really that, like, you don't have to buy into a specific library to do state machines. State machines as a concept can just be utilized. And you can utilize that with any— I mean, we do a lot of state machine-esque things or state machines in general in our codebase. We don't use any library to do it ourselves. So, I think that's really an interesting topic. What about— so, this is funny for me. Like, when you utilize it, there's a really interesting zooming feature. So, anytime you work with, like, a canvas, you, you think of like Figma or anything like that, you can zoom in and out of the canvas. And TL;DRAW, you can zoom in and out of the canvas. How do you handle the zooming? Are you increasing the size of everything? It's just like the blanket, um, component and you're, you're just scaling that and then everything else scales inside of it. What's the technique there?
Everything that you see on the page is the direct child of a div with zero height and zero width with a CSS transform. And that transform is transform— or like it's translating it. And it's also scaling it. And so, when you scale the parent, you also scale the children. Likewise, when you translate the parent, you also translate the children. So, That in itself, so all the children being absolutely positioned relative to the parent, which has a zero height and zero width, so it's almost like a single point, like an origin point. You're kind of like, you probably can't hear this, but I'm waving my hands around in the air. That allows you to move the whole canvas by and scale it as well. You have to do a little bit of math to figure out how to For example, if you zoom, you probably want to be zooming towards a certain point, right? You don't want to be zooming like to the top left of the page. And so there's a little bit of math involved in that. If you're curious, if you go to my blog, which is stevruiz.me, I have a whole article on that about like how do you do a zoom kind of or how do you do the camera controls basically for the Canvas app. And a bunch of other things related to TLDRAW and this type of project.
Yeah, this is going to be a super cool resource for anybody who uses TLDRAW and says, what the heck, how do I build something like this? Because you do really— I mean, that's how I first like started paying attention to your work was through your Twitter updates, right? All of the cool little things about your— your line drawings that you mentioned earlier on in the episode. So, uh, these things are really, really neat. Um, and if you're out there, go ahead and check out this blog because there's a lot of really fun, um, little nuggets that you can pick up from here.
Yeah. And if you don't mind the, uh, the early plug, uh, yeah, follow me on Twitter. It's— I'm, uh, @SteveRuizOK, uh, and I post a lot of kind of But I don't know. I mean, like the lucky— I'm kind of lucky that the things that I work on like lend themselves to very visual GIFs, you know? And like, um, so I, I sure do post a lot of those.
All right. Uh, so I've, I just downloaded one of my, um, what is it? I just downloaded one of the TL;DR files and it's literally every single point and color and arrow and everything that it did. So is that how you store these things? Is you just store the data of every single thing and like, where do you store that? Is that a database?
Um, okay. So TealDraw is multiplayer. You can go to, um, you know, like tealdraw.com/r, um, /syntax or syntaxfm. Let's do that. tealdraw.com/r/syntaxfm. And that is a document that is shared, right? It's collaborative. Any of those like tealdraw.com/r/whatever. So you should probably be able to see my cursor there, Wes and Scott. Right. So this is the multiplayer that we're using here is provided by Liveblocks, which is a service that does real-time data, a real-time sync. And this is stored, yeah, like on their servers. If you're just using TealDraw.com, everything is local. Like, we don't have— you don't have a login, uh, you don't have— we don't have our own database and such. So it's not in the cloud, it's just on your computer. You can save it to a file, which is essentially a big JSON blob like you were describing, um, and then you can open it back up So it uses files from your file system just like a normal app would, but it is a website. So, yeah, nice little project Fugu, I think, from Google to make those APIs for like local using a file, local files and such.
Wow. Oh, so you can save it to your— what? We've talked about that once, but can you explain that real quick? What is Project Fubu?
Fubu? Fugu. I think Fugu, like the fish, like the poisonous fish. Yeah, like that.
Yeah. Oh, not like the streetwear brand.
Project Fugu is a different project. I think the idea with Fugu is to— you look at a native app, it's like an answer to the people complaining that like, well, native applications can do things that the web can't, you know, and the idea there is just to narrow that gap as much as possible. So like, you know, one of the big things is, yeah, like I can load a file off of my file system. I can't do that on the web. And so they built APIs to let you do that, a file system API, which works pretty reliably. It's not fully implemented across browsers, but certainly in Chrome it, it, yeah, it works. Um, there's another way that you can use TealDraw with files. Uh, we have a Visual Studio Code extension, uh, which allows you to use TealDraw inside of VS Code. Um, and the fun part about this is that you can put your.tldr files just like right alongside your code. So let's say I'm working on a— let's work— I'm working on a state machine and I want to have a diagram that describes that state machine. I could create a little new tldr file from within VS Code, save it next to the code that I'm diagramming, and then like commit that to GitHub. So that my other colleagues or myself in the future can pull that down and again, like, view and edit the diagram, like, from within VS Code. In that case, you know, TealDraw is kind of like a glorified JSON editor. Wow. That's how VS Code sees it, just as another type of a text editor. But yeah, so working with Files, like, we don't, it's local, it's kind of like, yeah, we favor local stuff first. And we do have the multiplayer, which obviously uses servers, but yeah, you kind of have to opt into that. By default, it's all local.
That's pretty cool. So you don't have like 600 terabytes of people scribbling in a database somewhere.
I don't, no. I have, you know, 600 terabytes of my own scribbles that I've saved, but that's about it. Yeah, for sure, yeah. Yeah.
Did you say it was local storage?
Um, so we're using IndexedDB for persistence, local persistence, just because they do get— yeah, they can get big. We're not doing any clever, uh, compression or anything. Um, maybe someday, you know, make a ticket.
Um, can you explain to our audience, like, why would you want to use IndexedDB over, uh, something like local storage? Like, there's, uh, is there's a lot more features?
You have a smaller size limit with localStorage. localStorage is better in a lot of ways, but you can only store strings. So, you have to stringify everything and then unstringify it when you get it out of localStorage. And you only have, I don't know, like 15 megabytes or something? You don't have that much room to play with.
It's different for every—
Yeah. IndexDB is, I think, objectively like a worse API, but you can put objects there without having to kind of like stringify them. And you can also just put more stuff there. Like you get, you get a big chunk of the user's hard drive if you want. So that's why we do it. Wow. Yeah, that's cool. Yeah. So I mean, with TealDraw, the data is pretty straightforward. There's nothing, nothing fancy like GraphQL or anything. If you did want GraphQL, maybe you could check out today's sponsor, which is Gatsby.
Steve with the layup. Oh, wow. Love it. Yeah, he got it.
I can't believe, that's the first time we've had a guest do a sponsor, what do we call it?
Transition. Yeah, here we go.
Transition, yeah. So much of the brand, I love it. Amazing. All right, I'm jazzed, I'm feeling that.
Every time you nail one, you definitely—
Checks in the mail. Yeah, it gives you a boost. Scott lives on that high. I do. That's why he does it. Gatsby makes the hard parts of making a performant website much simpler with prefetching, lazy loading, and image optimization built right in. I personally use Gatsby on my own website. Go to westboss.com and see how fast it is. Uh, so if you're building a headless site or a content-rich site, Gatsby's GraphQL, they have a data layer, allows you to source content, uh, from literally anywhere. You can source it from files, you can source it from another API. That's somewhere on the website. You can— there's thousands of plugins that allow you to source data from. You can use it with one of our other sponsors, which is Sanity. You can source the data from that, um, and you pipe it all into the Gatsby GraphQL API, uh, and you can build your pages and your blog posts or any, any content types out from there. Also, what they have is Gatsby Cloud. You can bring your site to Gatsby Cloud and the cloud will optimize for Gatsby for faster builds and reliable previews. They'll, uh, they'll do all your image processing really fast as well. So you want to check it out at gatsby.dev/syntax. We should say, I didn't even mention this, Gatsby is a React-based, um, framework for building websites. You want to check it out at gatsby.dev/syntax. Thank you, Gatsby, for sponsoring. All right. Man, there's just so many things I'm curious about here.
We have like 10,000 questions for you.
I haven't even looked at the questions yet. How much code did you have to write to make it work on mobile as well? Is there a lot of like edge casey stuff? Or because you're using pointer events, does it work fairly smoothly?
Most things worked straight away. And this was another, I mean, the benefit of having a kind of like a tightly scoped app like TealDraw, it's a big app, but it doesn't do everything, is that I was able to spend a lot of time sharpening up the UX for mobile. And it works really well. I mean, if you load it up on your phone, even on like an iPhone or something, you'll be able to do everything you can do in a browser or on a desktop, like on your phone. You know, pinching should be smooth and dragging things around. Um, some of the events, especially around text, were a little bit different, especially on iOS.
There's some quirks about like gesture events, the keyboard open. Yeah.
Yeah. Uh, and yeah, there are still some things that could probably be made better. For example, there's, uh, it's possible for, uh, to hide the, uh, the text that you're editing when the keyboard opens. Like we don't zoom to make sure that that's above the fold. Um, but yeah, generally it was mostly about finding those, those few interactions that just didn't work, or assumptions that we had made about, about the browser APIs that, that just weren't there on mobile. Oh yeah. So I rely a lot on a library called React Use Gesture, uh, in order to do like pinching and, and panning and zooming and some of those gestures. So they've written really good gesture recognizers for JavaScript that you can use very easily in a React app. And yeah, that's what we're using for those gestures. And they work really well. Wow.
And what about service workers? Are you using service workers? Does it work offline?
I think it— I mean, we are— it is a PWA. You can install it in your browser on your desktop or on your mobile phone. I'm not sure if we've gone as far as doing the full offline. Uh, it might, it might work. I'm not sure. It does. I just tried it. All right, cool. Yeah, it works good. Right on. Then, then yes, I do. Yes, I do. Yes, I, uh, so, uh, yeah, this project again, like I've built it pretty much. I mean, I did build it solo in those, those 4 months. We've had some amazing contributors since then. Uh, but there are a lot of places where I was relying on just the ecosystem. So that was a Next.js app. The PWA stuff came through Next.js libraries that were designed for that. So, as much as possible, I was just trying to like— there were a lot of rabbit holes, but I wanted them to be in the app rather than in integrations or in things that wrapped around. I didn't want to have to write a pinch zoom gesture recognizer, but I'm very glad that I was able to find one that worked for us. Totally.
Yeah. Yeah. That, that doesn't sound like a ton of fun to me personally. Um, cool. Well, Steve, we have too many questions to ask you. I think we should probably have you on again. Otherwise this is going to get to like 2 hours long here. There's just too many things that we could possibly cover. So now I think we should, we should change course into the part of the show where we kind of ask you some questions that we ask everybody. Um, we, we're calling these dessert or supper club questions. We don't have a name for these yet, but basically we want to know what kind of computer do you use?
Oh, I use a MacBook Pro 14-inch 2021 model, I think. So M1. Nice.
Yeah, I'm sure that is useful when you're doing a lot of graphics-intensive anything. What about a keyboard? Any fancy or non-fancy keyboard?
Nothing fancy. Actually, my stack here is super simple. I have a nice mic. And I have a nice camera, but other than that, it's pretty much, pretty much just average off-the-shelf MacBook. Yeah. Nice.
Uh, what about, uh, text editor theme and font? Ooh.
Okay. This is good. Uh, VS Code, uh, Monokai Pro is my, uh, my theme. And I think I use the stock one, like none of the variants of that, but Monokai Pro is super choice. I've been using it for years.
Um, here's a question. If you had to start coding from scratch today, what would you pick up and try to learn? Like what even like type of thing? Would you go into the graphics world like you're doing right now?
Man, that's a hard one. I actually think I had a pretty good journey in terms of— I've only been coding since like 2017. So, it's not that long. Wow. But what I was doing when I started, I was using an application called Framer, which is now called Framer Classic, and just picking little micro interactions, little like design interactions and just coding those. So none of the issues of actually making a website, none of the issues of gluing things together, just being like, how do I make this button animate or rotate or something like only the most fun parts of coding. Is where I learned to code. And so, uh, I don't know, I would probably do the same. It's like, don't, don't worry about all the stuff that is, uh, not interesting and only focus on the parts that are, and you'll, uh, you'll, you'll get to the rest of the stuff later.
Yeah, I think it's a good point. You can, you can really, as long as whatever you're doing is, um, useful to someone, you could make a career out of doing what you find to be interesting and exciting. I personally totally, totally get that. Yeah.
Do you think like a lot of your— like, I'm trying to— I'm amazed that you're able to build such an amazing product with only having been coding, what, like 4 or 5 years now? Do you attribute a lot of that to your curiosity?
I think it's about like in my case, I— well, once I started, I kind of dug dug in pretty deep and spent a lot of time on it. But yeah, I think it's like I was lucky to have the ability to work on projects that— how do I say this? Because I was in this like prototyping space where I was more on the design org rather than the development org, there wasn't a lot of boring stuff. There wasn't a lot of cruft. It was really focused on making things feel good. And look good with code. And I was able to focus on that for years. And so, you know, learning interactions, animations, all that stuff, they introduce you to a lot of hard problems. A lot of the thornier parts of JavaScript and code. At one point, I wanted to make a pull-down menu that sort of had a liquid effect, where it's gooey as you're pulling it down. So, I'm like, oh, man, how do you do that? And I had to learn all about SVGs. That's where I learned about SVGs and paths and handles and all that. Um, and I don't think I would have encountered as many difficult problems, uh, which, which pushed me forward if I, if I had, you know, not to say there's anything wrong with just building, building regular websites. Uh, but I think that that was the, uh, I was just like swinging the heavy bat like every day. I was like in some really hard problems like all the time for years.
That's the best way to learn. That's the best way to learn. Let you, let it drive you forward. Your, your interests, the things that you're working on, the things that excite you. Cause it's funny because you say that like, those are the, those are the problems that aren't boring. Right. Um, because they're visually there. I mean, that to me personally, I agree. And those types of micro interactions are the things that are not boring, but some people would be like, man, database design. That's not boring. That's not boring stuff.
The actual stuff itself doesn't matter. I think the, uh, The other lucky part about doing these kind of prototypes is that I didn't have any pressure to actually ship it. And so it was just play. And I think that having to actually put this in users' hands at the end of the day or give it to a client makes certain things a lot harder. But then again, I like when people actually have websites and don't just have lots of fun prototypes. So, again, it's honest work, but I think that making that space for play is really the— I don't know, that's what had the biggest impact on my ability to code or how I learned.
Yeah, likewise. You seem to be the type of person who dives into topics a lot. What's a place that you go for finding new things in tech or staying up to date with what's out there in tech?
Right. I, I do read the Orange website. I do read the Hacker News. Uh, I think it's like not everything there is interesting to me, but occasionally I'll— it'll push me in places where I, you know, hadn't thought to go. Um, I, I take a lot of inspiration from video games. Uh, not— I'm not a huge video game player. I'm also not a video game developer, but I like to follow other people who are video game developers. There is a YouTube channel that I'm a huge fan of called One Lone Coder. This is mostly C++ content, but it is, uh, it's all the algorithms and the kind of small problems that you run into when you're creating a game engine or game design. So this is where I learned about making racetracks, which led to Perfect Freehand. And it is incredibly high-quality content. And even if you don't write C++, I mean, you can, you know, you can figure it out based on what they're talking about. So yeah, that's kind of where I go for inspiration and for programming. And yeah, for everything else, I could just go to Twitter.
I have a resource for you, a YouTube channel, if you like that one. There's a channel called Displaced Gamers. Um, I'll make sure I share the link with you. And this guy, what he does is he'll step through literal RAM values of NES games and show how modifying, uh, small bits of code. So he's getting into ROMs for NES games, but talking about these really clever techniques But there, there's, you know, uh, a video about how dithering worked on the Sega Genesis or, um, step-by-step CPU cycles for performance in Mega Man. It's, it's so like, like it's very far from anything that I'm doing, but I find it to be so fascinating. One of them, they just like step through the revisions of a specific area of code of a glitch in the original Super Mario Brothers where like it allowed him to glitch through a block and how you could see the evolution of the the program that they made over, over the course of the revisions to that game to try to prevent people from doing that. But I found it so interesting. They talk a lot about state machines in here too. Um, so yeah, I'll, I'll make sure you get the link if you haven't found it. But, um, yeah, really, really cool channel. I'll check out the one that you shared as well because that sounds like something I'm interested in.
There's also, uh, Coding Secrets, which is a former Sega developer talking about how they got how they achieved all these different effects on, on Sega Genesis. Um, I think you'd like that too. Yeah, that's cool. We could, we could, we'll trade. We'll take that offline.
I love this stuff. Yeah, I'm not a game developer either, and I'm no interested in being— well, maybe some interest.
They're just good. I mean, they're, they're, they're visual problems, they're small problems, and a lot of, a lot of indie game developers right now— indie games don't make that much money, uh, but content does make money. And so you have a lot of indie game developers who have like super strong communities and Patreon supporters and such, because like they, they share their videos about like what they're working on and how that, how it works. And I think that's beautiful. Awesome.
Well, uh, thank you so much for all that. It's super interesting. I could talk forever on, on this type of stuff. Oh yeah. But let's move it to the next section of the podcast, which is, uh, shameless plugs and sick pics. Actually, let's do sick pic first and then shameless plugs. Did you come prepared with the sick pic?
Yeah, yeah. Um, so I wanted to sick pic, uh, speaking of video games, there's a video game studio called Zachtronics. Um, they just put out a new, new game called Last Call BBS. Um, and I think this is the last game that they're making, this, this, uh, this particular game studio. Um, but a lot of their games are kind of appeal to, I think, programmers or people who are interested in electronics. They're like gamified versions of work, uh, like technical work. Um, cool, with a big vibe, like, uh, retro PC type of vibe. So Last Call BBS seems like some fantasy computer from like 1994 that, uh, that you, you get to open up and play different games and puzzles and such. Um, so yeah, definitely, definitely a big fan of of that studio and, and I hope that they continue making games perhaps under a different name, but Zachtronics is, uh, that's my sick pick. Super, super good. Um, uh, yeah, yeah, that's awesome.
Great. I'm, I'm like really excited to check this out.
This looks like something right down Salt's alley.
Yeah.
What about shameless plugs?
What would you like to plug? Shameless plug. We've talked a lot about like TealDraw as, uh, an app. But I've been spending the last— well, there's also TealDraw, the startup. We're turning TealDraw into essentially like a developer tool, like a platform and infrastructure so that other people— if you had an idea of saying like, well, I want kind of a canvas, but I want this to be for whatever, doctor annotations, or I want this to be for project managers or whatever your kind of Figma for X imagination can come up with. Um, go to tldraw.dev, um, and learn more about TLDRAW as like a developer, uh, infrastructure tool. So you can program your own, um, app on top of TLDRAW. It's going to be fun. That's really cool.
That's one of the first things I ever made with Canvas and WebSockets was literally this, and it was for doctors. It was for dentists. No kidding. That needed to, in real time, they needed to annotate X-rays of the patient's teeth. Um, and at the time they couldn't do voice, so they got on the phone and then drew on top of it so they could see it at the same time. And I'm just looking at this being like, this is exactly what we needed 11 years ago.
Also, can you imagine doing this? Very valid. Yeah, yeah, that's cool. That's cool.
Well, thank you so much for coming on. We appreciate all your time. This is super cool to hear about everything behind it and how you're approaching it. And now that it's a company, so, uh, best of luck with everything. Awesome.
Thanks for having me on. And yeah, there's plenty more to, uh, uh, plenty more that we didn't discuss about, about sponsorship, et cetera.
So there is, I know we didn't get into it, but someday, yeah, no, let's, let's put another one on the books for talking about sponsorship because, uh, that's, that's a huge thing, open source and sponsorships and whatnot. Like how do you get paid for doing open source? Definitely want to cover that as well. Cool.
Well, thanks so much, Steve, and appreciate the ad transition. Got to have you back on and get another one of those under your belt.
Absolutely. Thanks for having me on. Awesome. All right.
Thanks. All right. Thanks again. Cheers. Peace.
Head on over to syntax.fm for a full archive of all of our shows. And don't forget to subscribe in your podcast player or drop a review if you like this show.