The Propaganda Tiles, Math Edition

UIn the previous entry in the Propaganda Tiles series, I wrote about the history of the tiles, and my plans to sort them by color. It turns out this requires a dramatic amount of mathematics, almost all of which are miles above my head.

The primary field that works on this kind of image processing is the computer vision branch of artificial intelligence research. Luckily, there’s the OpenCV library – a vast collection of resources and program code – to help out. It’s another one of those remarkable open-source community-run projects that rivals any commercial solution.

I’ll be using some of the OpenCV libraries to process the Propaganda tiles and extract the top three colors in each image, along with the percentage of each. This will be done with a technique called k-means clustering, and this is how it works:

That’s from Wikipedia. I really have no idea what it means. I ain’t never had enough education to learn such fancy math. Heck, I couldn’t even get WordPress to draw a border around the image, so I had to replace it manually.

I realized this morning that searching for tiles based on a chosen color would be complicated. A color is a three-dimensional value, the most common being the levels of red, green, and blue. In the web world, these are expressed as a set of hexadecimal (base-16) numbers, like #a47eb1. That’s a4 (164) for red, 7e (126) for blue, and b1 (177) for green. These combine to make a sort of lavender purple color:

But it dawned on me that I can’t just “add X to blue” to find similar colors, because just moving along the blue scale isn’t helpful. If you take this color and fiddle with only the blue value, it ranges from purple to orange. Adding to or subtracting from all three colors just moves you closer to white or black. Not helpful.

There’s another way to represent colors: HSV, which stands for hue, shade, and value. This method is a lot less intuitive than red, green, and blue. The distinctions between hue, shade, and value are more difficult to grasp, at least for me. The Wikipedia page for HSV (and its cousin, HSL) runs to fifteen printed pages and includes diagrams like this:


Which is pretty, and it also makes a kind of sense of the whole HSV concept. But then the math comes in. Again. And you run into things like this:

It’s all three-dimensional computation, polar coordinates, vectors, and other mathematical concepts that are beyond my ability comprehend.

Luckily, I’m using OpenCV to do this work. It has a community of users. Users who are helpful and friendly. I asked my question on the OpenCV forums and got some helpful tips. It appears I don’t have any choice but to learn some of this math if I want my project to succeed. Or I at least need to understand how to use the OpenCV functions. Specifically something called flann. I’ll get back to you once I figure it out.

In the mean time, happy Propaganda to all, and thanks to the OpenCV members who shared their knowledge.


The Propaganda Tiles

This is a Propaganda tile.

It’s one of about 1,000 different square images that can be tiled edge-to-edge for a seamless effect. They make great desktop wallpaper.

They were created around 2001 by a Linux advocate named Bowie J. Poag. He wanted to prove the point that a Linux desktop could be every bit as visually attractive as a Mac or Windows desktop. In fact, he wrapped the roughly 17 volumes of Propaganda images in a nutty retro-scifi fantasy tale, starring JFK, who’d faked his death in order to promote Linux through the use of stunning imagery.

The Propaganda Tiles, while once relatively common, have now become a kind of urban legend. A subset of them was apparently shipped with Red Hat Linux at some point. It’s unclear if anyone has a definitive full set. I’ve kept my own copy on various flash drives and backup services for years. I found a set on GitHub to compare against. I compared my set against that and there were omissions and duplicates. I found another copy that still had them separated into the 17 (or is it 18?) individual volumes.

What no one seems to have, though, is that satirical JFK story. It apparently got lost while everyone was most interested in preserving the images themselves. I’ve searched all my copies. I’ve searched the multiple sets I found online. I’ve tried digging through the Internet Wayback Machine to find the original Propaganda site – which has been gone for about 15 years.

While the Propaganda tiles make for great wallpaper or other texturing projects, they’ve got one quirk that makes them difficult to use: their names. The swirly blue tile above is All-Good-People-3. There’s also an All-Good-People-2, which looks like this:

If you examine it closely, it’s the same geometric pattern, but with a different color palette. That’s the one naming rule that stayed consistent throughout all the Propaganda volumes. A trailing number indicated a color variation. Some have as many as 8 variations. But they all have nonsensical names. I don’t know how Bowie chose them. I like to think it’s some kind of surrealist non-statement. The only meaning is the one the viewer assigns to it.

The nonsense names are half the fun when browsing the tiles, but when you’re actively trying to choose a couple to use as wallpaper, it can be frustrating. You can’t remember which one was the cool blue one about two dozen clicks ago. Sure, you could expand your file browser into “preview” mode, but we’re still talking about a collection of over a thousand images.

So I’ve got a plan. And a programming project.

I tracked down the code needed to analyze images and identify the most predominant colors. I thought this would be a simple, if time-consuming process. I was wrong. In order to do it efficiently involves some complex math and statistical processing, most of which is covered by the computer-vision branch of artificial intelligence programming. The mathematics are way, way, above my grade, so I found a site that had a ready-to-use, free-to-use library to do the processing. I ran a handful of Propaganda tiles through it and saw that it would give me exactly what I wanted: the dominant colors in an image. along with the ratios.

So my plan is this:

  • Process all the images through the analysis tool, getting the top three (or five?) colors in each image
  • Stuff all this into a database
  • Code up an application that lets a user choose a color from a color-picking dialog (you’ve all seen those)
  • Find the best-matching Propaganda tiles by looking for that color in the database
  • Look for high-contrast or low-contrast tiles by comparing the “distance” between the predominant colors. A high-contrast tile will have a secondary color that’s vastly different than the most-common color. Think blue with yellow. A low-contrast tile will have similar shades of blue as all the predominant colors – not much distance between.
  • Allow the user to flag tiles as favorites.
  • Set their desktop wallpaper directly from the application, if I can.
  • Preserve Bowie J. Poag’s original tone of conquering the world through more attractive Linux wallpaper.

I believe this project will be called Propaganda For Plasma, as I’ll be using the KDE and Plasma frameworks to code the application. (The initial image analysis will be done in bulk beforehand, using Python, which seems to be the language of choice for the computer-vision crowd.)

And I’ll finally be able to do what I’ve wanted to – browse the Propaganda tiles by color. I love abstract backgrounds, but I’m picky about my colors. I’ve been getting through life well enough up to this point, but it’s a good project.

If I can make it all work, I may even stop using my folder of photos of The Clash as wallpaper.

Or not.

But at least I’ll get to spend more time with the Propaganda tiles.


Spectacle is KDE’s program for taking screenshots. I’d been pointed to its list of “junior jobs” – open bugs that should be fixable by new, aspiring, still-learning, wannabe contributors.

I chose one that sounded interesting and within my ability to fix. It involved adding a command to prevent the display of a popup window that confirmed that a screenshot had been captured. All the code was already in place; all I needed to do was add (or fix) that switch.

And I did that.

But then I started to do more. While fixing “nonotify”, I came across other functions that didn’t seem to be working, or not working properly. I proceeded to rewrite the help messages. I reworked and rearranged the input commands. I even added something I openly disclosed as feeling like a hack to make something else work.

I submitted my patch and waited for a reply.

And this is how I met Henrik. He’s what amounts to the project manager for Spectacle. Naturally, he’d be the one reviewing and approving my patch.

He reviewed it. But he didn’t approve.

I realized that I’d vastly overstepped my bounds. The bugfix assignment was a simple one. I didn’t stop where I should have. I got overly ambitious and added all those other “fixes” and “improvements”. Without a plan. Without understanding the bigger picture (no pun intended).

I was immediately intimidated by his disapproval. I felt like I was in over my head. I felt like a student who’d blown an assignment by not following the directions.

But it turns out that Henrik is actually a really good guy. We set aside the mess I’d submitted and he gave me other, simpler, tasks.

One was to figure out the cause of some warnings being generated by the automated compiler system. It’s name is Jenkins. Whenever a piece of KDE software is published, the Jenkins system compiles it, runs a bunch of tests on the code, and reports back all the successes and failures. It also logs any warnings – questionable code that could indicate a problem, but isn’t an error.

I looked at them and again thought they’d be easy fixes. Two lines of code needed, to wrap up and finish blocks of commands. I inserted them, compiled the program myself, verified there were no more compiler warning, and posted my fix.

Henrik took a look at what I’d added. He hadn’t had a chance to download my patch and try it himself, but he wanted to make sure I understood what I’d changed. I’m still learning C++ and how it handles common programming concepts. It’s different than other languages I’d learned. That’s where those warnings come from – program statements that aren’t errors, but are questionable and deserve review.

Henrik helped me understand exactly how this programming construct works (a switch/case decision block, for those interested in the gory details). He directed me to an online example and asked me to dissect it. I stated that one usage was incorrect and should be considered an error. Henrik reiterated that it’s not an error if the programmer wanted the end result that the code produced. It may not be good form or coded according to project standards, but it’s not an error. Hence the compiler warning. Not an error.

He also had me trace the sequence of events that occur in the program surrounding one of the warnings I’d silenced. It was an arduous task for an untrained C++ programmer, following the bouncing ball as it moved between blocks of code in numerous files.

But I learned the lesson Henrik was teaching me. It’s important that I understand the inter-connectedness of these programs. How all the various modules interlock to make a working whole. That I can’t simply drop a one-line fix into a big program. Maybe that warning is just a warning and the code is correct. Maybe my fix wasn’t appropriate.

We left things there and I went off on vacation.

I didn’t feel bad about this exchange at all. I’d been tutored by a senior developer, someone very familiar with the product being operated upon. He was patient and even light-hearted at times. But he was rightfully strict. He knew – better than I did – that you can’t just throw fixes out there and presume they’re correct.

As it turns out, my “fix” breaks the program. Henrik has left it up to me to find what I did incorrectly. He offered his help at a variety of levels, ranging from simply telling me what’s wrong to allowing me the opportunity to track down the problem on my own. It’s a generous and patient offer. Remember that I’m just supposed to be chasing down warnings, not fixing bugs. But by doing so, I apparently introduced at least one new bug – a real one. One that crashes the program, even though Jenkins wouldn’t complain about the code.

I’m up for the challenge. I think. Henrik is willing to help. I need to learn and understand what I’m doing. If I’ve got someone who’s willing to let me learn and explore, I’m going to take that opportunity.

I don’t feel intimidated any longer. Instead, I’m grateful for the mentoring. It may be unofficial and in the middle of live software updates, but I’ll take any lessons that I can get.

When I worked in engineering, senior people jealously guarded their trade and rarely – if ever – took the time to teach and share. Their work involved the secrets of the pyramids, and we junior people weren’t worthy. It frustrated me to the point of mental and emotional exhaustion.

But that’s not what’s happening in the KDE world. I’m participating. I’m definitely not getting everything right on the first try, but I have people willing to help me. And teach me. Who’ll let me learn from my mistakes without abusing or insulting me.

That’s the key of the free and open-source software community. It’s a community. Everyone’s a volunteer, from the project manager to the newcomer, wannabe bug-squasher. Share your finished product, share your knowledge of programming.

As it turns out, I’ve worked out a revision to an earlier fix for Spectacle. I believe I’ve solved the problem in the way Henrik intended. I wrote up my findings for him and am waiting for his comments before submitting my code.

I’m learning. We’ll see how well it’s going in the next round of review.

Triaging Leads To Fixing

As that more-senior KDE contributor wrote on Reddit, keep looking through the bug reports. Maybe you’ll find one you can fix.

I spent some time going through the day’s bug reports, trying to confirm or replicate the reported error. I ran across a number of interesting problems. Some I could recreate, others I couldn’t.

At the same time, I was teaching myself how to code plasmoids. I made two just for my own use. One changes your screen resolution by querying xrandr, listing the available resolutions, and issuing the command following a mouse click. I needed it because I work by remote, and NoMachine wouldn’t always reconnect at my preferred resolution. I went ahead and added the ability to filter the resolution choices by aspect ratio (16:10, 16:9, etc.) It works pretty well.

The other checks uptime and displays your system uptime in a small horizontal panel widget. While doing this, I learned how to code regular expressions in JavaScript. I wanted the uptime display as condensed as possible, so I had to regex every possible variation that uptime would spit out. At this time, I was still tinkering with my machine a lot, and there was a lot of rebooting.

I ended up polishing them enough to submit them to for the world to download. Each one is sitting at the default 50% enthusiasm score, so ScreenRez and Uptimer didn’t exactly set the world on fire.

But I was learning QML, its quirks and complications.

I continued to work the day’s reported bugs, seeing what I could see. Then I found one. It seemed straightforward enough – a combo box in a plasmoid was too small and the option text was getting cut off. I figured I could fix it.

I spent a day hunting around, trying to figure out if I needed permission to work on it. Or to get it assigned to me, something like that. Finally someone on IRC told me, “You don’t need permission to fix something, just go fix it.”

And so I got to work. It was one of the stock plasmoids, so I made a copy of what was installed on my system and started picking it apart.

QML elements can be tricky to resize and align, at least in my limited experience. Since everything is a child of something else, various properties of the parent dictate how the child is going to behave. Just like real life, I guess. Getting that combo box to accept a size bigger than the default was trickier than I’d assumed.

But I finally got it. And fixed a related problem where the description of the chosen option wasn’t updating like it should. And even changed a default setting to a more sensible and less-random seeming number.

This was Bug 390571, and I fixed it. I got a little education from David Edmundson, one of the Plasma & plasmoid gurus. It’ll be distributed as part of Plasma 5.13.

After years of using and admiring open-source software, I’d realized a small version of a personal goal: contributing something back. It’s a small fix to a minor widget for your desktop. I didn’t reinvent the wheel or cure cancer or radically shake up the world of KDE development. But should you choose to use Media Frame to display photos in a widget on your desktop, I had a hand it making it work right and be user-friendly.

That’s pretty cool.

Sidebar: Stockholm

I’m writing this from a hotel room in Stockholm. We’re on a break from life in the States, visiting chilly but pleasant Scandinavia. Yesterday was a 5-hour train ride from Copenhagen, via the ├śresund Bridge, as I first saw it in the Danish/Swedish crime series “The Bridge” (“Bron/Broen“).

There wasn’t much to see except snowy, wintry Swedish farmland, so I spent most of the journey shopping for a KDE laptop. Unfortunately, I had to settle for doing so over 3G; the train’s expected free WiFi wasn’t working. It matched a mixup with our seat reservations, which resulted in a few polite expressions of discontent from a few otherwise friendly Swedes.

I think I’ve settled on the Acer Aspire E15. It’s got a full keyboard (with keypad) and a proper IPS 1920×1080 full HD screen. It’s only got 8GB of RAM, but the processor is a quad-core eighth-gen i5. It’s got a 256GB SSD and room to expand. I think this will work for my first dedicated Linux laptop.

I asked for buying advice on Reddit, which led me to re-reading an earlier question I’d posed about how to get started participating with KDE.

The answer I got was thorough and comprehensive:

I now recognize the username as the same senior KDE contributor I’ve asked to mentor me as I learn. I’m following Nate’s method as best I can. Starting out small and making small fixes as I find them.

I’ll spell out the details of how this has been working in future posts. Now it’s time to go sightseeing.

Getting Hooked On KDE

It hasn’t been that long, but I’ve already forgotten what first got me hooked on KDE. I’d used Linux in the past, but only in a passing, utilitarian way. Something about KDE caught my eye, though. Maybe it was the eye candy of the Plasma desktop. Maybe it was learning that Plasma is powered by Qt technology, which I’d learned a bit of while tinkering with PyQt.

I had an ancient PC in my basement that was running Mint Linux, which I chose a year or so ago, reading that it was one of the easiest distros to get up and running. Its primary purpose was to be a Plex server, for streaming all my media.

The time came, though, when that old box couldn’t keep up with the large file sizes and higher resolution video files. I’d just gotten a 4K HDR television, so I wanted a machine that could stream and transcode effectively.

I bought a $400 AMD-powered desktop and connected it to an even-more-ancient 5:4 LCD monitor. I resumed connecting to it with VNC. After hooking up my external media drive, I realized it had more than enough power to transcode my movies and collection of Scandinavian crime shows.

I started to play more with Python, which led me to PyQt. I’d never programmed a GUI before, but I understood Python and could make it work.

I’m pretty sure that’s how it flowed. Python -> PyQt -> Qt -> KDE Plasma.

I was immediately jazzed by what I saw on the Plasma desktop. Widgets. Applets. Plasmoids. I learned those were written in Qt’s markup and layout language, QML. And the underlying logic could be straightforward JavaScript. Heck, I could learn those things.

And so I got to work learning something new.

A new start

I registered this domain back in 2007 and never did anything with it. I figure it’s time I did something – anything.

I’ve been paying hosting fees for 10+ years, although my provider,, has made this as inexpensive as imaginable. Yes, that’s a plug, and no, I didn’t get anything for it.

And so, it’s a blog. I’m so cutting edge.

Over the past six months, my interest in technology and programming has re-emerged. I’ve been programming again. Originally in Python, now I’m trying to learn C++. I’ve gotten hooked by KDE, a Linux-based organization that’s created everything from a desktop environment to an incredible range of pro-quality, entirely-free software. They’ve been around more than 20 years, so something good must be going on.

I’m going to try documenting my journey, sharing what I learn as I go. I’m only a year away from turning 50, but I’ve still got so much to learn.

And so I figure I’ll bore the rest of you with the ins-and-outs of a graybeard old dog who’s trying to learn new tricks.