Exploring Picotron (Part 1)

ยท 840 words ยท 4 minute read

What is Picotron ๐Ÿ”—

From the official website,

Picotron is a Fantasy Workstation for making pixelart games, animations, music, demos and other curiosities. It has a toy operating system designed to be a cosy creative space.

Essentially, it is a simplified operating system/workstation that runs on top of mainstream OSes. Its primary purpose is to allow its user to build pixelart games and make other fun stuff. For those who are familiar, it is like the big brother of Pico-8, which is fantasy console by the same developer.

I have heard of Pico-8 in the past but have not spent any time exploring it. My interest in Picotron was piqued when I saw its very positive thread on Hacker News and I decided to pick up a copy.

A screenshot of Pictron

This post documents how I gained my bearing exploring Picotron.

Goal ๐Ÿ”—

There are a lot of things that I need to figure out before I can do anything meaningful on Picotron. My immediate goal is to build my Hello World for UI frameworks – a counter app. It has a button and a number – the number goes up whenever the button is clicked.

First steps ๐Ÿ”—

I went through the user manual. This has been a good overview of how to use Picotron. It also includes a simple demo app to showcase how programs are written in Picotron.

In general, every program has three main functions:

  • _init, which is called once when the program starts. This can be used to do a one-off setup, such as to set the title of its window.
  • _update, which is called consistently 60 times a second. It is used to maintain the application state (for e.g., handle key presses, etc).
  • _draw, which is called to draw the UI on the screen.

I also watched the Introduction to Picotron by Lazy Devs.

Lua ๐Ÿ”—

Picotron supports only Lua. The only thing I know about Lua is that it is an embeddable language. I found that a good way for me to quickly pick up a new programming language is to skim its Wikipedia page to get a quick taste of the syntax. Thankfully, it seems that Lua’s syntax is not too esoteric and what is shown on Wikipedia is enough to get me started. In the near future, I would probably want to go deeper into metatables and Lua’s OOP mechanisms.

Picotron “standard library” ๐Ÿ”—

My understanding is that Picotron does not use Lua’s standard library. Unfortunately, Picotron’s API documentation is not ready at the moment. The good news is that practically everything in Picotron is source-available, so we can look at how other people wrote their programs. Each program is packaged as a cartridge and shared on the Lexaloffle BBS. One of the first cartridges I explored was minesweeper, which has all the elements in my Hello World app – buttons and click handler. To check out the code:

/> load #picotron_minesweeper

This will put the minesweeper cartridge in /ram/cart. Opening up the code editor and we can see its source code. In its main.lua, I see references to gui, such as create_gui, gui:attach_button, and gui:update_all, but I can’t find where these functions are defined. Hence, they should be part of the Picotron standard library.

Next, I recalled that in the video by Lazy Devs that the programs shipped with Picotron – such as the Terminal, Code Editor, and File Navigator – are all userland applications. In other words, they are built with the same set of tools as we have. These built-in programs live in /system/apps. In theory, I could open up these programs and look at their code within Picotron. However, the code editor in Picotron is really not great to navigate and explore unfamiliar code bases. A better way is to copy them out to the host OS (i.e., the “real” OS) and look at the code with a “real” text editor. I decided to copy the entire /system directory since it is filled with a lot of other goodies:

/> mkdir output
/> cp -r /system /output
/> folder /output

I think one of the best built-in programs to start with is the “About” app – it is simple enough yet covers a good variety of functionalities such as interactive UI. Looking at /system/apps/about.p64, we can see references to the same GUI-related functions as before. I did a full-text search for function create_gui in the /system directory and see that it is defined in /system/libs/gui.lua. I also spent a bit of time looking at other files in /system/libs – it seems that this is the yet-to-be documented standard library.

Hello World ๐Ÿ”—

With all these resources, I am ready to build my Hello World app in Picotron:

local gui
local counter

function _init()
        window{
                width = 150,
                height = 100,
                title = "Hello World",
        }

        counter = 0

        gui = create_gui()
        gui:attach_button{
                x = 10,
                y = 10,
                label = "Click me",
                click = function()
                        counter = counter + 1
                end,
        }
end

function _update()
        gui:update_all()
end

function _draw()
        cls(10)
        print(counter, 1, 1, 1)
        gui:draw_all()
end