Retrospective

The arcade machine has been completed for about four months now. I have added a few arcade games and gone through the process of pulling out the control panel and updating the Arduinos and the SD cards a few times. Every time, something went wrong. A wire breaking, an Arduino not taking the sketch, and so on.

So this post is about things I learned and things I would do differently.

Cabinet

For the cabinet assembly, there are a couple of things. The first is that I would use a table saw for my straight cuts (e.g., the back, front, top and bottom panels). Whenever possible, I would also use the table saw for the mitered cuts, like the ones below the control panel. Secondly, I would make the dado cuts a little wider. I used 3/4” MDF and made 3/4” dado cuts. The pieces fit very snugly into the cuts. In fact, they fit so snugly that I had some issues when I was gluing it all together. So I would probably make 7/8” dado cuts for 3/4” MDF.

Electronics

On the electronics side, the biggest issue is the difficulty in updating the images for the button labels. Some things I would do differently there:

  • Drive the Arduino inputs directly with the GPIO on the Pi rather than going through a relay bank. I used the relays because I was not sure whether the Pi could handle the load, but the inputs are high impedance, and I could still power the Arduinos and displays in parallel with the Pi. I love the click of the relays, though!
  • For the connections to the main board, use snap connectors such as Molex instead of connectors with screws or soldering wires (especially solid-core wires) directly to the board
  • Use a low-assert relay for the peripherals
  • Use a GPIO ribbon cable instead of DuPont wires to connect the Pi to the main board. This would also mean soldering a connector to the main board for the ribbon cable, and connecting the peripheral relay to the main board instead of to the Pi (with another snap connector)

I would say that I would choose a more convenient place to store the button label images, but I have yet to find a display that small that can load images from a different source.

Of course, I have no intention of ever building another arcade machine. I’m glad I built this one, and I love it. The effort required to make another one would not be worth it when I already have one. So this post is, as I said, just reflection.

I will make a “Look at the cool thing that’s all finished” post soon (I think) with cool photos and videos of the finished product.

Electronics installation: power button, internal wiring, and control panel

I decided to put the power button on the top of the arcade, on the left side, near the back. The threads on the button I chose do not extend 3/4”, so I had to drill a larger hole part way up from the bottom to accommodate the nut.

The button has a normally open and a normally closed contact, so I used the continuity setting on my multimeter to determine which two contacts I needed. I bent the normally closed contact slightly to mark it.

Then I fed the wire through the nut and the hole to solder the connections. I put some shrink tubing on the wires so could cover up the connections.

Here it is installed

Next I clipped the wires to the proper length, and added the connector to plug in to the control panel.

At this point, I had all the connections needed for the control panel, so I connected them and installed the panel.

The last step for wiring was to get power into the cabinet. This required a hole for the power plug socket. This needed to be a mostly rectangular hole, so I drilled three smaller holes and used the reciprocating saw to cut out the wood between them. It didn’t turn out pretty, but it will work. I’ll put a bit of epoxy putty in the gap at the top.

Nothing that will ultimately be plugged in inside the cabinet uses the grounding pin, so I didn’t connect it. The wire I am using has red and black insulation, so I followed the RV wiring standard instead of the house wiring standard, which is that black is common and red is hot.

There will never be much stress on the outlet box inside the cabinet, so I attached it with adhesive instead of screws.

I also used them on the transformer for the amplifier.

The design required the Raspberry Pi to have constant power while the power for all other components is switched through the relay controlled by the Pi. So I put in a power brick and plugged everything but the Pi into it.

I put it up near the marquee since it also has 5V USB sockets on it. That way I could plug the marquee LEDs directly into it and not reauire a separate USB power adapter.

To make one outlet switched and one constant power, I needed to break the tab connecting the two outlets on the hot side.

Th next step was to wire up the outlet as follows:

  • Red wire coming in from wall power to the top outlet hot side
  • Black wire coming in from wall power to either outlet common side (I chose the top)
  • One wire from the relay to bottom outlet hot side
  • The other wire from the relay to the top outlet hot side

This wiring will make the top outlet constant power and the bottom outlet switched. I originally just wrapped the wires arounf the screws and rightened them, but since these are stranded wires, they spread out under the screw and it didn’t look like a good connection. So I tinned the ends with solder, and it went much better. Here is is all wired up:

I plugged everything in and tested it. The first time I loaded a game, the labels didn’t light up. I pulled the control panel out and saw that the positive wire for feeding power into the relay bank circuitry was disconnected. I reconnected it and everything worked.

So now all the components are installed and functional. There are a few final cosmetic touches and it will be done!

Control Panel Support

Since the cabinet turned out to be slightly narrower than I had planned, I trimmed out the left profile so the control panel would fit. I also carved some notches in the front MDF piece to accommodate the GPIO connections.

The angle aluminum I bought to support the bottom of the ci trol panel was 36” long. I bought that size because it cost less than having them cut it to a 30” piece. And now that the cabinet is slightly narrower than I had planned, I would have had to trim it anyway.

I put the piece of angle aluminum on the cabinet and marked where I wanted screw holes. I drilled small pilot holes and used those as guides to make pilot holes in the MDF. Then I drilled out the holes to the proper size and used a countersink bit on the aluminum. Then I screwed the aluminum in place.

The bottom and both sides of the control panel are now really well-supported. I decided to use the piece of aluminum that I had cut off of the long piece to add some support to the top. Since the circuit board goes all the way to the top of the control panel, I positioned the aluminum between two mounting screws so it could fit between the circuit board and the control panel base. Since the narrow piece of MDF behind the control panel was now being used for support, I reinforced it with some shelf brackets.

Cabinet Assembly

The final home of the arcade machine will be my basement, so I decided to assemble it there instead of having to get the fully assembled cabinet down the stairs. I set one profile on its side and then started by connecting the floor to the back and the front pieces. I put glue in the dado cuts and also on some 1×1 boards along the seam, which I held in place with nails.

Then I put that assembly into the dado cuts in the profile (with some glue) and added the reinforcing 1x1s. I repeated the process for all the cross pieces, and then added the second profile.

I had forgotten that the 1x1s in the back should go top-to-bottom so that they would also create a ridge to support the door. So at the bottom I just did my best to line it up with the one I had cut.

Once I had both profiles on, I clamped it and left it to dry. I didn’t put any reinforcing 1x1s on the second profile because that’s much easier to do when you’re working with gravity instead of against it.

While I was waiting for the glue to dry, I added feet to the bottom, using furniture levelers attached to blocks of 2×4.

Once the glue had set, I flipped the cabinet to the other side and added the 1x1s. Once that glue had set, I stood the cabinet upright.

Because the dado cuts were such a tight fit and so close to the edge (I probably should have used at least a 13/16” bit instead of 3/4”), there was some cosmetic damage that occurred during assembly. I will need to repair these and also add filler to the seams on the front and top back before the cabinet can be painted.

Another issue is that when I measured and cut the cross pieces for the cabinet, I failed to account for the width of my saw blade. So now the control panel doesn’t quite fit.

To remedy this, I plan to cut away some of the wood under the cut for the angle aluminum that will hold down the panel.

I tried to see how well the marquee would fit, and that’s when I realized that I should have cut these slots all the way to the edge of the board.

Now that the cabinet is assembled, I don’t think the router will fit there, so I’ll likely extend those cuts with the reciprocating saw.

Final trimming and dry fit

I had all of the pieces for the cabinet cut, but I needed to round off the top back corner of the roof piece, and the piece right above the front piece needed to be trimmed a bit.

I need the curve on the roof piece to be a 100-degree curve and not 90, so instead of using a router, I marked where I wanted the curve and used a file and sand paper.

I filed down the two ends first and made sure they fit.

Once I had the entire edge filed down, I went over it with some 120-grit sandpaper.

Once this was done, I trimmed up the piece above the front with my circular saw. Then I put all the pieces together to check the fit.

Some of the joints will need some filler, but it all fits pretty well. I added the control panel and TV just to see how it would look.

In the previous image, you can see that the wires connected to the GPIO on the Raspberry Pi are right up against the wood. I actually need the control panel to slide down a little further, so I will chisel out a notch for the GPIO connections after the cabinet is assembled.

The last step before beginning assembly is to cut a T-mold slot in the roof piece, as well as a slot for the top of the marquee. The marquee slot has to line up with the slots on the profiles, so I measured carefully and found that they were off from each other by 1/8”. No big deal; I just need to cut a slightly diagonal slot in the roof so it all lines up. Being off by 1/8” over 30” will not be noticeable.

The other issue with the slot in the roof is that it has to be 10 degrees off of perpendicular so that it will line up properly. To achieve this, I bought an adjustable angle base for my router. It has angle marks every 7.5 degrees, so it set it to about 1/3 of the way between 7.5 and 15, and did a test cut.

It was right on.

I also used this test cut to measure the fence distance I would need for the angle base. The notch lines up perfectly on one side, but is slightly off on the other.

I might just chisel a little out of the notch on the profile so that the marquee can easily slide into the roof notch.

Next step: assembly!!!

Cutting the hole for the amplifier bracket

The amplifier will be in the center of the front panel, a few inches below the control panel. I measured and marked the hole, and double-checked that the fit was good.

I used a drill and reciprocating saw to cut out the rectangle. I cut it a little small because the thin blade on the reciprocating saw doesn’t always cut straight, and I wanted room to clean it up. Once the main hole was cut, I slowly cut away bit by bit until the bracket fit.

Here it is with the amplifier in place

I will have to use some filler on the left side and maybe a little along the top, but once it’s all painted it should look pretty good.

Power Button

When the arcade is completely built, I want it to have a button somewhere on the cabinet that acts as a power button. That is, pressing the button will cause the Raspberry Pi to boot, the TV to turn on, the marquee to light up, and the speaker amplifier to have power. Pressing the same button again will cause the Pi to shut down, and everything else to lose power.

Step 1: Toggle Pi between running and halt

I thought I was going to have to use a latch circuit, because I was under the impression that the only way to make a Raspberry Pi boot after a shutdown was to remove and restore power. But then I found out (by finding this: https://www.instructables.com/Raspberry-Pi-Power-Button/) that shorting pins 5 and 6 on the GPIO header will boot the Pi from a halt state. And then, to make this same connection cause a shutdown while it is running, you only have to add one line to /boot/config.txt:

dtoverlay=gpio-shutdown

Step 2: Use the Pi to control power to other components

So I can connect a momentary pushbutton to pins 5 and 6 and have a power button that does what I want, at least for the Pi. I can then use the Pi to control a relay that will control the power to everything else. Since everything ultimately is connected to AC power, I will use the relay to interrupt the AC line to everything but the Pi. That relay is already installed on the back of the control panel.

I connected the 5V pin on the relay module to pin 2 on the GPIO header, the ground to pin 9, and the control to pin 3 (GPIO 2). Then I wrote a python script called ‘turnOnPeriph.py’, which looks like this:

export RPi.GPIO as GPIO
import sys
GPIO.setmode(GPIO.BCM)
GPIO.setwarnings(False)
GPIO.setup(2,GPIO.OUT)
GPIO.output(2,GPIO.LOW)

Then I added the following to /opt/retropie/configs/all/autostart.sh

# Turn on the relay that powers all peripherals
python /home/pi/bin/turnOnPeriph.py

It turns out that the relay is high-asserted, and the default state of GPIO pins is high, so the relay is activated as soon as the Pi has power. Once the autostart script executes, the relay is deactivated. This means that I will have to connect the AC line to the normally closed contact instead of the normally open. The only weirdness this will cause is that the marquee may flash briefly when the unit is plugged in or unplugged.

Step 3: Force Pi to load HDMI

So now we have a power button for the Pi, and the Pi switching on power to the rest of the system. But there’s more work to be done. By default, the Pi tries to detect a monitor on HDMI at boot, and if it doesn’t, it will not load HDMI, and there will be no output even if you connect a monitor later. The reason for this is that the Pi gets the resolution and refresh rate settings from the connected device and loads HDMI with those settings. This is a problem if we are using the Pi to turn on power to the TV.

Fixing this is a two-step process. First, add (or just uncomment if it’s already there) this line to /boot/config.txt:

hdmi_force_hotplug=1

This will cause the Pi to load HDMI regardless of whether a device is connected. Since the Pi won’t be able to get the resolution information, the second step is to tell it what settings to use. This is done by running raspi-config, navigating to “advanced settings,” then to “resolution,” and then selecting the option that corresponds to your output device. Of course, you have to know what the correct settings are. You can do this by executing the two following commands:

tvservice -d <file>
edidparser <file>

My TV is advertised as “720p”, but its native resolution is actually 1366×768. The refresh rate is 60Hz, so the correct setting is HDMI_DMT_1366x768_60

Step 4: Use HDMI-CEC to turn on the TV

Now the Pi will correctly load HDMI, and once the TV is powered and turned on, we will have our display working. Which leads to the next issue: when you plug in a TV (effectively what I’m doing with the relay), it does not automatically turn on.

Fortunately, the TV I bought (along with 99.9% of TVs made in the last decade or so) supports HDMI-CEC, or HDMI Consumer Electronics Control. I had to go into the menu on the TV to turn this on. Then CEC has to be installed on the Pi. That was easy enough to do following the steps provided by PiMyLifeUp (https://pimylifeup.com/raspberrypi-hdmi-cec/). With this installed, I can add the command to turn on the TV to my autostart script, and it should be ready to go.

However, the TV isn’t ready to receive CEC commands the instant it has power, so I need to be sure that it’s ready before I send the command, or it won’t work. If you query the power status of an HDMI-CEC device that is unplugged, the result will be ‘unknown.’ I added a while loop checking for status so that I know when the CEC module is responding. Here is my updated autostart.sh:

# Turn on the relay that powers all peripherals
python /home/pi/bin/turnOnPeriph.py

# Wait until the TV  has booted to  send 'on' signal
status='unknown'
while [[ $status == *"unknown"* ]]
do
  status=`echo 'pow 0.0.0.0' | cec-client -s -d 1`
done
echo 'on 0.0.0.0' | cec-client -s -d 1

emulationstation #auto

That should be all the setup required for the power button. All that’s left is the wiring!

Securing the joysticks, and LED wire connectors

I tried just using the same screws that I have for the standoffs to secure the joysticks to the control panel, but I didn’t trust that to hold. The holes for mounting the joysticks are just too big.

I decided to use the washers that I had used to mint the joysticks on the old control panel, but with the thickness of the washer plus the metal plate of the joystick, the 1/4” screws were too short. I got some 3/8” screws, but they were ever so slightly too long.

So I rummaged around in my toolbox and found more washers so I could stack them to keep the screws from poking through the control panel.


Once the arcade is built, I don’t plan to update the images on the SD cards very often. But I still want it to be possible without extreme amounts of trouble.

The extenders for the SD cards that I used before are not really practical anymore, because in some cases the ribbon would have to be creased in order to fit. This of course risks damaging the ribbon. Here is an example of where the extenders just don’t work.

So when I want to update the SD cards, I will have to get the displays out of the control panel, which means removing the large “Play Anything” circuit board. This means removing the 16 mounting screws (I may put Loctite on the threads of the standoffs so they don’t come out when I try to remove the screws) and disconnecting the wires from the relay bank.

But since the circuit board also will be driving the LEDs inside the buttons, I will have to disconnect those as well.

Disconnecting the wires from the button blade connectors is quite a hassle, and the negative lead is a long daisy chain. So I decided to connect the LED wires to the board with mounting posts. It took a while to find any kind of wire-to-board connector that was for only a single wire. And many of those still require two holes in the circuit board, which won’t work for me. I settled on these:

One potential problem with this approach is that I put the mounting hole for the negative wires too close to one of the Arduinos. Luckily, the mounting post fits and clears the Arduino. I will have to unplug that one to access the screw on top of the post, though.

Here is a section of the board with the mounting posts installed:

Some simple power consumption calculations (that I should have done a long time ago)

I knew that 20 AWG wire would be much more than adequate to handle the required amount of current for the LCD circuits. I went that large because I also wanted some structural enhancement after the stranded wires kept breaking. But I was curious to see just how much current those wires would be handling.

Each circuit board drives one 5V, 16MHz Arduino Pro Mini, one LCD, and one LED. The current draw of the LCD is 25 mA, according to Adafruit. The Arduino Pro Mini (5V) draws up to 26 mA when running the default “blink” sketch ( see https://www.arrow.com/en/research-and-events/articles/getting-started-with-the-arduino-pro-mini#:). It’s been long enough since I bought the arcade button kit that I don’t know the LED current draw, but the maximum current for a standard LED is 20 mA. So each board can potentially draw up to 71 mA. The largest current draw on the 20AWG wires will be on the segment between the relays and the first board, since that segment has to supply the current for all ten boards, or 710 mA. 20 AWG wire is rated for up to 3.5 A under continuous use. So, yeah, the wires I chose have a capacity of almost five times the current they will ever have to carry.

But I was surprised at how high the final number was. We’re approaching a full amp, and that’s just for one side. Granted, that is the maximum current that should ever be drawn, so games that don’t use all the buttons (and thus don’t light all of the LEDs and LCD backlights) will use less. Still, there is a potential for the LCD functionality to draw up to 1.42 A (710 mA per player), plus a little more to drive the coils of the relays.

I took a look at the power supply that I have been using for this circuit. Maximum output is 300mA. This led me to a question that I didn’t like: was inadequate power the only reason this didn’t work with the previous design? I quickly decided that I didn’t care about the answer to that question, because I like the new design so much better. Also, I immediately ordered a 3A power supply.

More soldering, and an updated procedure

I jumped the gun a little when I soldered the wires between the first two boards. I had the foresight to solder in the Arduino socket before soldering the board-to-board wires, but I should have also soldered the wires for the LCD of the downstream board before connecting the boards together. The board-to-board wires cover up the solder points for the LCD wires, so for the board I already did, I have to either unsolder the board-to-board wires or bend them enough to allow access.

So the new procedure is:

  1. Install two adjacent boards to the control panel. The downstream board should have nothing soldered to it.
  2. Measure, cut and strip the board-to-board wires.
  3. Remove the downstream board from the control panel.
  4. Solder the Arduino sockets to the downstream board.
  5. Reinstall the downstream board to the control panel.
  6. Add wires to the LCD and attach a positive wire to the button LED. Measure, cut, strip and tin these wires.
  7. Remove the boards from the control panel.
  8. Solder the LCD and LED wires to the downstream board.
  9. Solder the board-to-board wires.

It may seem inefficient to remove the board, add the sockets, and reinstall the board instead of just soldering the sockets and the LCD-LED wires to the board at the same time. But I want the sockets on there when I measure out the LED/LCD wires so that I have a stronger visual cue of where the Arduino will be, and I should be less likely to cut those wires too short.

In order for step 6 to work, the control panel needs to be assembled with the buttons and LCDs in place. So I reassembled the control panel and connected all the wires for the joysticks and buttons. Then I attached the LCD/LED wiring for the first circuit board, and added the Arduino socket for that board.

Then, before moving on to adding the LED/LCD wires for the second board, I added the wires that run from the relays to the first board.

That doesn’t look as clean as the ribbon I had there before, but it’s more robust and durable. I may spend some time at some point making the bends in the wires more uniform, but for now I will focus on getting the rest of it wired up.