'Analogue' low res digital waveforms


#1

I was just thinking, the way low-res saw and triangle waves were generated could be driven by a high frequency VCO instead of integer division of a high frequency clock. Such an arrangement would give you something that is analogue in the time domain and digital in the amplitude domain.

Does anyone know of a module that does that? I’m aware of Edges, but that’s fully digital as far as I’m aware. Perhaps this is something I should breadboard (at least the latter half of it, not the VCO bit).


#2

Hi,
There was a discussion about this recently on the SDIY mailing list. Very doable, even inside a single MCU (which have very high-resolution timers). I haven’t tried yet.


#3

But doing anything within an MCU is by definition discrete time rather than continuous even if the sample rate is very high. I fear you might have missed my point. You’d need to do it with “discrete*” logic chips like CMOS 4000 series to keep time continuous (i.e. not sampled).
A counter being clocked by the VCO, an R-2R DAC to ‘weight’ the square waves. To do a triangle, you divert the MSB and use it to XOR the other bits.

Thanks for the link though!

*I know discrete is very much the wrong word, but I can’t think how else to describe it.


#4

Wait, I might have indeed. You want to clock the generation of samples by an analog VCO, right? At each clock tick, a new sample is output? This is discrete time too…


#5

Sorry, please see the lengthy edit above. No, no samples - just a logic circuit that runs at an audio rate that is clocked by a high frequency VCO.


#6

Send your signal into a whole bunch of analogue comparators, and mix all the comparators’ gate outputs. Example: if you mix the four normal gate outputs of the AniModule Quad Comparator, you’ll get a 4-bit signal. But you’ll need to attenuate the gate signals before mixing, or else you’ll run out of headroom.


#7

Hmm… Sorry, I know very little about electronics; would you mind reformulating your idea in terms of signals (I don’t know the components you’re referring to)?

If I read you correctly: incrementing a counter each time a clock ticks, and converting the result into a (quantized) voltage is driving the generation of a new sample by a clock… am I wrong?


#8

@mqtthiqs
Found some cool stuff in that thread already:

>One nice feature of the STM32 is the ability to use an external pin to clock
>data out of the DACs via DMA.
>i.e. you can set up a block of samples (S&H data, audio waveform, etc.) to
>be cyclically loaded into the DAC, and have an external signal (e.g. PLL’d
>analogue oscillator) drive the output at a variable sample rate with no CPU
>overhead.

That’s really cool! While it isn’t precisely what I was suggesting it’s very useful to know. I bet that’s how the Modal Electronics oscillators work - I know they use a variable sample rate like the old PPG Waves.

@C14ru5

Ah yeah, that would let you ‘bit crush’ an analogue input without actually sampling it into discrete time. That would be an alternative to generating it from scratch for sure. I definitely still want to try my approach - building a staircase wave and then optionally flipping half of it to get a stepped pyramid.


#9

@mqtthiqs

It is sample based in a way, the sample rate is just an exact multiple of the pitch and is continuously variable because it’s driven by a VCO. So my current line of thinking is:

HFVCO four octaves higher than the note you want driving a counter or a bunch of chained dividers to derive squares at -1 octave to -4 octaves. That’s effectively a 5-bit counter, if I sent that straight to a simple DAC then I’d get a stepped ramp with 32 steps.

Instead what I do is send the 4 LSB (that is squares 0, -1, -2 and -3) to individual XOR gates and send the MSB (the -4 signal) to the other input on all of the XORs. This inverts the top half of the ramp to make a triangle that goes 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, a, b, c, d, e, f, f, e, d, c, b, a, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0. This is how plenty of old sound chips generate their triangle, the difference is that they were clocked by divisions of a master clock. If it was driven by a (HF)VCO, much fun could be had.

I realise that with divisions of a high enough master clock the pitch resolution issues would be negligible, but I would still get a certain satisfaction out of knowing that the pitch was constantly variable.


#10

Ok I see, thanks. If I’m correct, what you want is unquantized time, but quantized amplitude (analogue or digital is not the matter here), to avoid aliasing.

So you can do it with CMOS, or you could drive the DAC of an MCU by an external VCO (phew, too many acronyms) at n times your pitch… what I learned, and my point above, is that you can also do it straight within the MCU (at least with STM32s): the time will be quantized, but the frequency resolution is such that you shouldn’t hear the “stepping” from one pitch to the next.


#11

Ah, I just read your last sentence. Satisfaction is another thing, surely! I wish I had the skills to design it in analog too :wink:


#12

Yeah, I didn’t realise you could do that so thanks very much for that link! My understanding is that if it can be driven externally then even inaudible stepping might be avoidable. Unfortunately I’m no programmer so the CMOS solution appeals greatly to me.

I don’t really have the skills to design this, but I do like messing with CMOS on a breadboard!


#13

Good luck then!


#14

Random notes:

  • The XOR thing you describe is indeed the NES triangle.
  • Walsh functions: you can approximate any waveforms by stacking enough “octaves” of square waves - including square waves obtained by division of a master clock. Korg Poly 800.
  • Some old-school wavetable VCOs work like that: analog ramp VCO at 1x the original frequency into an ADC into the address lines of a ROM / EEPROM into a DAC. Or you can do it this way: analog ramp VCO at 256x the original frequency into a counter, into the address lines of a ROM / EEPROM into a DAC. The former requires good calibration of the ramp shape and scale/offset, so that each output code of the ADC is generated as the ramp goes up.
  • The Modal stuff is not analog - it’s just an ATMega or the like, and one sample sent at each timer interrupt - the interrupt rate is equal to the frequency x the wavetable length.

#15

>Walsh functions: you can approximate any waveforms by stacking enough “octaves” of square waves – including square waves obtained by division of a master clock. Korg Poly 800.

I suppose that makes sense, it’s almost what a simple DAC is doing anyway.

>Some old-school wavetable VCOs work like that: analog ramp VCO at 1x the original frequency into an ADC into the address lines of a ROM / EEPROM into a DAC. Or you can do it this way: analog ramp VCO at 256x the original frequency into a counter, into the address lines of a ROM / EEPROM into a DAC. The former requires good calibration of the ramp shape and scale/offset, so that each output code of the ADC is generated as the ramp goes up.

Hmm, but wouldn’t you run into problems with imperfections in the saw? After all, it’s impossible for the saw to reset instantaneously so you might get an incredibly quick backwards read through the wavetable. Wasn’t there a thread about this recently? But the subject was reading it into an MCU rather than directly (without sampling) controlling the memory lookup.

By the way, I didn’t mean to suggest the Modal stuff was analogue, but that it used a variable sample rate rather than a fixed rate with resampling of the wavetables.


#16

Tangential, but I remember reading that the Noise Engineering Basimilus Iteratas Euro module uses a variable sample-rate, which they claim is a feature, because any aliasing artefacts track the base pitch.

a|x


#17

> Hmm, but wouldn’t you run into problems with imperfections in the saw?

Yes we would! But if we’re interested in perfect solutions, then the problem is pretty much solved with an MCU and band-limited wavetables.


#18

In a lot of my Reaktor blocks, I let the user override the main timing accumulator with a “scratch” input. This lets any waveform replace the boring ramp wave. It also allows for things such as envelope generators and 64 step sequencers to act as waveshapers. Even my quantaized random block can work like this thanks to the variable bell curve distribution.

This is definitely one of my absolute favorite sound design techniques. Yes this is in the digital domain, but because of that we can have a ramp that takes 0 extra samples to go from 100% to 0%. The other cool thing is that since it is still a free running ramp wave, you will get small wrapping errors that will give you minor shifts in phase and waveshape. Overall, perfect pitch tracking of the base ramp, and minor errors in the final output that ensure no two back-to-back waves are the same.

Giving the user access to the main timing ramp also lets them hook up several step sequencers in parallel to get many time synced rows with an individual number of steps. Say one sequencer with 15 steps and one with 9 steps. With the shared accumulator, they will both always share the same down beat.


#19

Here’s an example from 1985: the Digisound-80 80-21 VCDO

And an example of one in the Science and Technology Museum, London:

Alas, I don’t have one in my Digisound-80 cabinet.

There are several eurorack versions of this, such as the Malekko Richter MegaWave (see the historical notes on that page).