#0002: Prototype 2, Commands, botches and Linux

Presentation:

Well alright. Since the last weeks update, a whole lot has happened. Having more or less assembled a rudimentary handheld system in it's most strip down, core state, I could start working on the features of text input mechanic. For starters, I decided to play around with various Fonts, see how they look on the screen and make sure they take just enough space to fit a handsome, literary rich paragraph while taking up as little space as possible and still being legible all together. If only I knew about the absolute drastic change which was about to occupy me for the entirety of the following week... Here are some "beauty shots" of the fonts

Trying out a smaller font here: IMG_20191117_211818.jpg

Sound and Audio:

I've also received some of these LM386 amplifier boards. I've ordered some standalone ICs too, however since I was getting kinda antsy to try playing around with audio right then and there, and the fact that those ICs would only arrive in about a month from now, I have decided to just get bite the "expense bullet" and get these handy dandy ready-made guys for prototyping. I gotta tell ya, the "Support Local Business" tax is brutal, I tell you h'wat. For 5 of these, I could have ordered about 40 more of standalone ICs, plus all the individual components (minus the pcb) to make my own amplifiers. But oh well, that's the cost of locally and readily available parts.

IMG_20191119_140816.jpg

Now, the good news is that they worked. The bad news is that I've destroyed one of the DAC channels on the Due. Ok, ok, now these amplifiers had nothing to do with it so no worries, there are no parallels being drawn between the two. The problem is that I'm an idiot... and at some point I've wired the DAC directly to 5v... yeah... Now after some googling, I found out that apparently I'm not the first idiot who had lost a digital to analog converter to this trap. In fact the Arduino Due, according to many forum posts, lacks reverse current protection on the DAC0 pin, which DAC1 pin, and many other pins, gets to benefit from. Many have lost the feeble DAC0 to bad wiring or overloading it with a honker of a speaker. Although the arduino web resource DID SAY that I was free to test the audio on headphones, (which is a low load but they didn't say anything about connecting it to 5 volts), for a moment there, it did sound pretty good.... well.. ya know... before it died screaming in pain that is... now that pin just sounds like dial up mode... so bonus :/ ?

IMG_20191119_140827.jpg

Botches:

Now of course we cannot have prototypes without a couple of botches. As it turns out, I did not wire the backspace and enter buttons to the right channels on the schematic, before sending for fabrication, causing myself quite some time of grief while wondering why instead of the Enter key, this thing kept typing the letter L.

Enter key, correct routing

Of course since the keyboard is multiplexed, we can't just simply limit the botch to a single key, no,no,no. The backspace also fell victim so that too had to be rerouted. A couple of quick wires snips with te ol' box cutter knife and we were back in business. Fixed it up in the schematic files too so that's progress.

Backspace Key, correct routing.

That was fun...

IMG_20191118_171628.jpg Both buttons with fixed witing

Basic Input:

So once the keys were all in order, it was time for the fun part - the firmware. This is the actual game. The core mechanic, the reading of the key inputs, the parsing of the user commands and the processing of the game database files. I've started with some simple commands to get the ball rolling.

CLEAR: Clears the screen of all input.

LOOK AROUND: prints the description of the room that the player currently in.

any other commands which the parser did not recognize would result in the game printing:

"I do not understand' to the screen

testing out the commands

And with this I had to take a long hard look at this project and face the undeniably crushing question.... how the hell am I going to pull this off? See there was really only one biggest problem I have to face with this - Limited Resources. The idea of using an MCU (Microcontroller Unit) is that I have to deal with some severely limited resources. Mainly memory, never-mind processing power. Memory is the most precious resource in a project like this. This project has a bunch of some pretty heavy demands in store for it. Polyphonic Audio (Music and sound effects playing at the same time), Displaying icons, sprites and images, working with large database files among other medial related features that escape me at the moment. Yeah, that's is indeed a tall order for a micro-controller. Its by no means impossible, however it is very quite tricky and time consuming. usually when you code software for a computer, in my experience, I've had to deal with very little memory management. This is in part due to the fact that many of my projects have been developed on pre-existing frameworks, which in turn were developed specifically for ease of use and peace of mind. Mainly i'm talking about Game Development Engines and Web Development Platforms. Game Engines handle a wad of background featured for you, they handle resource manage so that you don't have to. All you do is make the game within ballpark of common sense (Engines can't fix bad code border-lining on incompetency) and that saves you a lot of time. Same thing with web development on a smaller scale, we're not talking about data processing here. Small tools, small websites, simple database queries. Now the MCUs on the other hand throws all the out the window. All of that ease, frerdom and abundance of resources - gone out the window right along with your comfort zone.. I've been spoiled by Javascript, Python, PHP and many game engines with their proprietary interpreted languages, abundance of resources and processing power that even thinking about how in the world am I going to approach this media heavy project with so (arguably) few resources available felt like a monkey wrench being thrown into my spokes.

IMG_20191119_225117.jpg Probing around the DUE D/A converter pins to find out why the hell the audio is not coming out of one of the channels. PS: If Reeses cups would like to sponsor me, I am totally gonna bite.

So here's the biggest problem:

There is too much data. This is not really the question of processing power, it's the question of memory. There is too much that needs to be stored in the memory and that is not the worst of it all - the worst of it is that the data increases and shrinks in size.

So let me explain. If I want the game to have inventory then that means that I need to store that inventory somewhere in the game. Ok, no worries, just allocate some memory on the controller for some inventory and store the inventory there. Ok now the inventory is something that I'd like to be scale-able. It needs to be able to shrink and expand. You need to be able to pick up some items from the game and put them into the inventory. Guess what, not only will the inventory expand but the room database will shrink. That item you've just picked up has to be stored somewhere and that somewhere is the memory of the MCU. Not only that, I'd like the player to be able to upgrade the inventory which means that it would be able to store more items and thus the memory allocation demands for the inventory are going to become much bigger. On top of that, we're not storing any measly peace of data, oh no. We're storing stuff like item ids, item descriptions, item weight (inventory limited by weight), item prices for in-game economics as well as quest items which cannot be removes unless used to complete a quest and suddenly we come to a point where in order to be able to handle inventory alone, we would need to know - what is the most theoretically largest amount of items could the inventory carry and how much memory will that hypothetical inventory eat up. That would technically be a solution, however it will this mean that for the majority of the game, there will be a humongous chunk of memory just sitting there, unoccupied but reserved and inaccessible to any other features.

This is where the idea of dynamic memory comes into play, a concept where you can expand and shrink memory allocations as the need arises, however that unfortunately is a slippery slope to basically rendering much of your memory unusable for scale-able applications. Mainly it's very easy to allocate memory but not be able to expand it because after the memory for the inventory has been allocated there's other data being declared / stored in the memory and thus no further expansion of this allotted memory can take place.

mem.png

You have to start watching your memory allocations like a hawk. Memory doesn't move around, memory stays in the same place and we're not even talking about audio and images yet.

All the other medial which I would like to incorporate into this project like stylized icons, item sprites, large world map, screen effects, mini-games that need graphical assets, music, sound effects and a whole lot of GUI elements - all demand memory, not to mention that many of the features like the LCD display driver and the Adafruit GFX library already eat up a chunk of memory just by existing (running) on your device. Memory management wise, this is suddenly becoming quite a game of Tetris. Now it's not impossible but I must again ask myself. Do I want to finish this project and get it out into the world as fast as I can or do I want to experiment to see IF I can make this happen by constraining myself to an MCU? The inventory alone is a huge undertaking and frankly, I feel compelled to tackle it on. But the problem is that this would mean that I will be taking on this project with a one hell of an ass backwards approach. The way you go about it is - list your demands and then find a platform that can satisfy those demands - not pick a platform and then try to figure out how the hell you're going to achieve this as a self proclaimed "challenge".

And with that in mind, after about 3 years of laying on my desk... I have finally unwrapped one of these.

Raspberry Pi Zero

IMG_20191119_233616.jpg

A Raspberry Pi Zero. Tiny, Compact. Same as my first Generation Raspberry Pi. Has a butt-load of resources and is quite frankly pretty much a-lot like coding software for a computer... heck... it IS a computer. A mini computer but a computer nonetheless. The resources this thing offers quire frankly feels like an all you can ear buffet after working on an MCU. Let's see what we've got.

  • 1GHz, Single-core CPU
  • 512MB RAM
  • Mini HDMI and USB On-The-Go ports
  • Micro USB power
  • Composite video and reset headers
  • CSI camera connector
  • 802.11n wireless LAN
  • Bluetooth 4.0

So the biggest differences are 512Mb of ram, Built in Bluetooth and Wifi as well as a dedicated HDMI port for a monitor. This eliminates some of the biggest resource eaters (LCD driver on the mcu) and also simultaniously solves many of the things I was planning to implement in terms of connectivity - Wifi (for web console controls), Bluetooth (For.. well... same thing but bluetooth) and an LCD display output.. WHICH MIGHT I GOD DAMN ADD THAT IT LOOKS CRISPY CLEAR! I mean just look at this sucker!

IMG_20191120_130817.jpg raspberry pi hdmi lcd display from Kedei

VS this piece of shit.

IMG_20191117_211756.jpg arduino mega HX8347 driven display running off a parallel port that apparently out of entire China, only one single seller ever sold, and I happen to have bought it right before it was abolished by law... but really I'm just frustrated that it took me over a year before I got this thing working with quite a bit of outside help

Now to be fair this was a one old ass LCD display. That blueish tint around the sides... that's the back-light. I know, it's atrocious but it kinda gave off a sort of charm of it's own. Almost retro, to be honest. The difference is also in the price. about $8-$12 Canadian rubles for the TFT LCD display vs about $22 for the HDMI, the extra buck is well worth it tho... Anyways, this is all behind us now. It's out with the old, and on with the new (ps no I'm not tossing it out, are you kidding me, it's perfectly fine for what it is.)

IMG_20191121_013251.jpg

IMG_20191121_013246.jpg

From the top... this time with Python.

Getting acquainted with rasbian was quite an experience. It wasn't as bad as my past experiences have been due to... well... inexperience with Linux. But times have changes, online has grown fat with knowledge-bases, resources and forum posts so it wasn't too bad at all.

IMG_20191120_140447.jpg rasbian lite up and running

I snatched a second keypad (I got a total of 5 of them since that's the minimum order quantity... and good riddance. I'm on my 2nd one), fixed the botches, populated it with pins, buttons, wires and resistors and got it all wired up to the RPi.

IMG_20191121_145716.jpg

IMG_20191122_020107.jpg

The screen looks great and even at this small of a resolution, the text is very quite legible. Now of course the final game won't be using fonts this size, it's more a statement to the fidelity of the display.

IMG_20191121_215612.jpg

And it's a bit wider than the LCD on the first prototype too so bonus points. It's not too much wider as to look too futuristic.

One thing that I'm not a fond of is this blue screen, blinding branding here. That is a one ugly greeting method. I was contemplating on implementing some sort of a micro-controller imposed delay mod, which would wait before powering up of the lcd back-light until this annoyingly gauche splash screen would go away but apparently there is already a solution available. You can override the splash screen graphic with your own so hey, bonus marketing points to this project as I'll be able to superimpose my own branded graphic right on the lcd bootup:

https://github.com/floppes/RTD266xFlash

20191122_192839.jpg nasty lcd display splash screen. Definetely will be removing this using the tools in the github above

I've set up the programming environment that is interestingly enough quite reminiscent to Web Development. I'm coding on Windows using Notepad++ since it's much easier than IDLE and I didn't want to deal with the bloat of PyCharm so I opted in for the path of lowers resistance. I'm logged in to the RPi over SSH using WinSCP which allows me to quickly transfer updeted python program and resources to and from the pi. It feels kinda like working with FTP server wen working on Web Dev so it feels right at home. I'm able to rapidly deploy the updated application to the pi while working on windows and benefiting from the Notepad++ offerings. Neat-o-Burrito.

In Conclusion:

Before calling it a day, I've decided to commit to this prototype and solder the wires onto the Pi. so we went from this:

IMG_20191122_020107.jpg prototyping the pins of the keypad onto the RPi

To this:

IMG_20191122_162749.jpg RPi Zero Connected via a one thick ass HDMI cable. Going to have to find one of those flex ribbon hdmi cables for this one.

And thus the two prototypes side by side: IMG_20191122_163510.jpg two prorotypes. Left running on Due with a crotchy ass-blue LCD tint (had to re-use the sd card on the pi so no text output on the Due) Right. Pi Zero with the crispy HDMI display

This article is my 2nd oldest. It is 2710 words long, and it’s got 1 comment for now.