Peace for All – Re: Factor

birdculture1 pts0 comments

Peace For All – Re: Factor

Peace For All | Re: Factor

Re: Factor

Factor: the language, the theory, and the practice.

Peace For All

Wednesday, July 8, 2026

#games

#text

#ui

I am perhaps susceptible to nerd-sniping and it<br>often leads me down interesting rabbit<br>holes. Today was<br>one of those days. I bumped into a fun<br>article<br>about some obfuscated bash<br>code on a T-shirt for<br>sale:

The obfuscated code in question is actually an easter egg, it’s being<br>supplied via Uniqlo stores on an excellent t-shirt designed by Akamai in<br>support of their Peace for All campaign.

While reading about the author&rsquo;s use of<br>OCR to<br>convert the printed text into a string that they could compute base64 --decode on to see the resulting program, I had major nostalgia for<br>carefully typing programs from computer<br>magazines so they could be<br>run locally – the only option for us kids at the time.

Raylib can be a great tool for doing colorful<br>animations and is pretty well supported by Factor.<br>I thought it would be fun to show how to write a similar program using it!

First, we define some constants for our message (infinitely looping using a<br>circular<br>sequence), font<br>sizes, text colors, and then a computed number of visible text rows:

CONSTANT: message $[ "♥PEACE♥FOR♥ALL" ]

CONSTANT: width 800<br>CONSTANT: height 600<br>CONSTANT: font-size 24<br>CONSTANT: freq 0.2

! colors move from cyan to orange<br>CONSTANT: color-start S{ Color f 0 255 255 255 }<br>CONSTANT: color-end S{ Color f 255 135 0 255 }

: rows ( -- n ) height font-size /i ;

The default font doesn&rsquo;t include a heart glyph, so we need to be able to<br>manually draw one:

:: draw-heart ( x y color -- )<br>font-size :> s<br>x s 0.30 * + >integer y s 0.32 * + >integer s 0.22 * color draw-circle<br>x s 0.70 * + >integer y s 0.32 * + >integer s 0.22 * color draw-circle<br>x s 0.50 * + y s 0.95 * +<br>x s 0.92 * + y s 0.42 * +<br>x s 0.08 * + y s 0.42 * +<br>color draw-triangle ;

Otherwise, we draw our character as a function of a &ldquo;tick&rdquo;, moving<br>horizontally in x according to a sine<br>wave, and changing colors within<br>our color range:

: wave-x ( tick -- x )<br>freq * sin width 4 /i * width 2 /i +<br>round >integer 0 width font-size - clamp ;

: wave-color ( tick -- color )<br>[ color-start color-end ] dip rows mod rows /f color-lerp ;

:: draw-glyph ( tick row -- )<br>tick wave-x :> x<br>row font-size * :> y<br>tick message nth :> ch<br>tick wave-color :> color<br>ch CHAR: ♥ = [<br>x y glyph color draw-heart<br>] [<br>ch 1string x y font-size color draw-text<br>] if ;

We can now define a rendering function that we use each tick, that draws a<br>glyph on each row:

: render ( tick -- )<br>begin-drawing<br>BLACK clear-background<br>rows [ [ + ] keep draw-glyph ] with each<br>end-drawing ;

And then a simple loop where we open a window, and increment the tick and<br>render each frame:

: open-peace-window ( -- )<br>width height "♥ PEACE FOR ALL ♥" init-window<br>30 set-target-fps ;

: peace-for-all ( -- )<br>open-peace-window 0<br>[ window-should-close ] [ [ 1 + ] [ render ] bi ] until<br>drop close-window ;

It looks pretty good!

The code for this is on my<br>GitHub.

© John Benediktsson 2008-2026

color peace draw tick font constant

Related Articles