Glyptodont performed on the... Qwertar?
My SID tune Glyptodont performed live on a new C64-based instrument.
Update 230726: It's called the C=TAR!
- Linus Akesson - Glyptodont Live.mp3 (MP3, 7.5 MB)
The C64 is running a modified version of Qwertuoso loaded from an autostart cartridge.
Introduction
Phrasing and dynamics are important in music, especially in the case of slow soulful melodies. In my ongoing adventure of converting Commodore 64 computers to musical instruments, I've tried to approach expression control in several different ways.
My Theremin offers precise control over pitch and volume, but the instrument is very difficult to play. The Commodordion uses a bellows for dynamics, but it's too heavy and unergonomical. For Monty on the 'Bin and Vocalise, I routed the SID audio through a simple volume knob next to the keyboard. This worked well in practice but was kind of unimaginative and visually underwhelming.
One thing I learned from the Commodordion project was that although the instrument was unwieldy on the whole, playing the right-hand-side keyboard—the one that remains stationary in front of the body—felt quite good. So with that in mind, I decided to build an instrument resembling a guitar. I went through a couple of iterations before settling on the final design. The first idea (which came to me in a dream, actually) was to have a little cart sliding on linear bearings along metal axles, and a rotary encoder to pick up the motion. The cart would have pushbuttons and a microcontroller on it, and the signals from the buttons and the encoder would be transmitted to the C64 electronically over the axles.
Distance meter
So I bought a couple of shafts and bearings and figured out a way to attach them to the C64. Three rods would be enough for power distribution and a simple serial communication protocol. But I couldn't find a good way to mount the rotary encoder while maintaining good friction against the rods. I eventually scrapped that idea and decided to use a distance meter instead of the encoder. A laser-based time-of-flight sensor would be able to measure the absolute distance between the cart and the C64, and would even be able do so from the other side—mounted on the C64 itself. This would simplify the communication, perhaps to the point where no microcontroller would be necessary.
I settled for a distance meter module called Pololu 4064 (but other makes should work just as well). It has a 500 mm range and operates autonomously. The module can run from 5 V, which is conveniently available on the C64 user port, and has a single digital output signal. As explained in the video, the distance meter works by measuring the time of flight of a laser pulse, but this event only lasts for a few nanoseconds and would be too fast for the C64 to observe directly. The output signal from the module is also a pulse with a width that is proportional to the distance, but the signal has been magnified (slowed down) a million times and is on the order of 1–2 ms. This translates to about 1000–2000 clock cycles on the C64.
We can put one of the CIA peripheral chips in the C64 in a special mode where it increments a timer only when one of the CNT inputs (on the user port) is high. The maximum resolution is half the C64 clock rate which gives us 500 distinct values, roughly one value per millimetre.
To synchronize the C64 application to the measurement cycle, we connect the output from the distance meter to CNT2 but also to the active-low FLAG2 interrupt pin. In this way we get a non-maskable interrupt just after each incoming pulse. When the interrupt arrives we can read the measurement value from the timer register and reset the timer in anticipation of the next measurement.
Touch sensors
Having come this far, I still had a vision of a sliding cart with buttons to control various functions. But I noticed that the half-finished instrument looked kind of cool with just the rods sticking out. Perhaps I could do away with the cart entirely, and measure the distance to my hand instead! But what about the buttons?
As explained in my Theremin video, when you move your hand near an electric conductor, its capacitance to ground increases very slightly. If you actually touch it, the change is even bigger. You can drive a piece of metal to some known voltage—let's say 0 V, ground level—and then charge it slowly through a resistor to a different voltage, such as 5 V. By measuring how long it takes for the metal to reach an arbitrary threshold level, let't say 2.5 V, you can estimate the capacitance—and this allows you to detect touch.
But the signals leading into the C64 are highly sensitive to electrostatic discharge (ESD), so it would be irresponsible to connect them directly to the metal rods. Instead, I designed a buffer circuit based on a quad op-amp chip (LMC660). This chip can run from a single 5 V power supply.
PB7 is configured as an output from the C64. It's connected to a voltage follower that drives its output to 0 V or 5 V, charging the rods through three large resistors. The remaining three op-amps are wired up as open-loop comparators. The voltage on each rod is compared to a fixed 2.5 V rail created from Gnd and 5 V using two 10 K resistors. The outputs from the comparators will be fully maxed out and close to 5 V or 0 V, so they resemble digital signals and can be sent back to the C64 through PB0–PB2.
The op-amp chip affords a certain amount of ESD protection, and even if it were to break down it would be easy to replace. If a voltage spike manages to get past the chip, it will be tamed by the 1 K resistors before reaching the C64.
Between measurements PB7 is held low for a long time, allowing the rods to reach ground level. To start a measurement cycle, PB7 is raised. A few clock cycles later, PB0–2 are sampled. If they've already reached a high level at this point, the capacitance was low, meaning the rod was floating. Otherwise, the capacitance was high and the rod was being touched.
It's important to always read the result a precise number of clock cycles after raising PB7. No interrupt or DMA should get in the way. It's easy to avoid DMA interference by checking the current raster position and delaying if a badline is about to happen, but what about the non-maskable interrupts repeatedly generated by the distance meter? The solution is to simply run the touch sensor code from within the distance-meter interrupt handler.
The code
Here's the C64 code for interfacing with the sensors. First we need to initialize the CIA timers and the interrupt vector:
lda #$7f ; turn off all interrupts from CIA #2 sta $dd0d lda #$ff ; timer B will count down from $ffff sta $dd06 sta $dd07 lda #$01 ; timer A will count down from 1 (in a loop) sta $dd04 lda #$00 sta $dd05 lda #$00 sta $dd01 ; PB7 is initially low lda #$80 sta $dd03 ; PB7 is output, the other bits are inputs lda #$91 ; start timer A sta $dd0e lda #<nmi ; set up non-maskable interrupt vector sta $fffa lda #>nmi sta $fffb lda #$90 ; enable FLAG interrupt sta $dd0d
And here's the interrupt handler:
nmi sta savea+1 ; save register A lda $dd0d ; acknowledge the interrupt ; handle the distance meter lda $dd06 ; read timer (the register won't change now) sta distlsb lda $dd07 sta distmsb lda #$79 ; restart timer B and configure it sta $dd0f ; to count timer A overflows when CNT is high ; handle the touch sensors waitdma lda $d012 ; get raster Y position and #$06 cmp #2 ; badline coming up? (assumes default screen mode) beq waitdma ; yes, wait some more lda #$80 ; charge rods (set PB7) sta $dd01 nop ; wait a certain number of cycles before reading bit 0 ; (you may have to adjust this based on e.g. rod size) lda $dd01 ; read PB0, PB1, PB2 and #7 eor #7 ; rod is held if voltage is low, so let's invert the bits sta heldrods lda #$00 ; discharge rods (clear PB7) sta $dd01 savea lda #0 ; restore register A rti ; return from interrupt
Naming the instrument
(Updated 230726)
As mentioned in the video, I had a hard time coming up with a good name for this instrument, so I reached out to the community for help.
After receiving several great suggestions, I finally settled on The C=TAR. Here's a brief video announcement of the new name.
Posted Friday 7-Jul-2023 10:51
Discuss this page
Disclaimer: I am not responsible for what people (other than myself) write in the forums. Please report any abuse, such as insults, slander, spam and illegal material, and I will take appropriate actions. Don't feed the trolls.
Jag tar inget ansvar för det som skrivs i forumet, förutom mina egna inlägg. Vänligen rapportera alla inlägg som bryter mot reglerna, så ska jag se vad jag kan göra. Som regelbrott räknas till exempel förolämpningar, förtal, spam och olagligt material. Mata inte trålarna.
Greg Knox
Sat 8-Jul-2023 02:35
\m/ ( -_- ) \m/
Ralph Corderoy
Sat 8-Jul-2023 07:47
Sat 8-Jul-2023 09:42
Sat 8-Jul-2023 13:29
"C6T4" a C3PO variation which will sound exactly right ~ Si-Six-Ti-For .
But for this instance with the special C64 instrument with a .... Trident?
How about something includes Treudd (Trident in Swedish) for the new instrument name?
Like
Treuddont (as the first instrument's song was Glyptodont)
(which will sound Triudont)
or Treudd-(t)ar (which will sound Triud-ar).
I have to admit other suggestion sound a lot better though .
Sun 9-Jul-2023 09:50
PS! Great stuff 10/10 as usual
Sun 9-Jul-2023 21:24
Keep up the very very creative work you're doin'
/Kuddel
Mon 10-Jul-2023 00:18
* Theremon - theremin + ML monitor
* CIAtar - for the 6526 + guitar
Sat 15-Jul-2023 20:45
Wed 19-Jul-2023 07:17
Sat 29-Jul-2023 12:22