A recipe for a simple FM kick drum.


I tried to build this to be highly parametric, so the core function fmkik has a lot of variables, all lambdas except for ft:

trig is the trigger signal.

freq is the frequency of the kick (in hz).

c, m, and i are the carrier/modulation/index FM parameters. The index is being enveloped, so i is the initial amount.

dst is the overdrive distortion level (simple limit distortion). 1 is normal, anything greater will cause some sort of clipping.

len is the overall hold time length of the kick.

tail controls the decay time of the amp enveloped.

body controls the decay time of the modulation index (timbre) envelope.

ft is the sine ftable, as a lambda.

(define (fmkik trig freq c m i dst len tail body ft)
  (let* ((t (monolith:mkcab trig 0))
         (trigf (lambda () (cabget t))))
      (display t)
      (cabget t)
       (param 0.0001)
       (lambda () (expon (trigf) (i) (body) 0.001))
      (mul zz zz)
      (mul zz (dst))
      (limit zz -1 1)

      (cabclr t))))

The core components of the kick are a retriggerable sine oscillator, and from that a retriggerable FM oscillator.

(define (fmkik-sine rt freq ft)
    (tphasor (rt) (freq) 0)
    (trd zz ft))

(define (fmkik-fm rt freq car mod indx ft)
  (let* ((o (lambda (f) (fmkik-sine rt f ft)))
        (freq-reg (monolith:mkcab freq 0))
        (fr (lambda () (cabget freq-reg)))
        (car-reg (monolith:mkcab car freq-reg))
        (c (lambda () (cabget car-reg)))
         (lambda ()
            (mul (indx) (mul (fr) (c)))
            (o (lambda () (mul (fr) (c))))))))
      (display "freq-reg: ")
      (display freq-reg)
      (display "car-reg: ")
      (display car-reg)
      (o (lambda () (add (mul (fr) (mod)) (car-osc))))
      (cabclr freq-reg)
      (cabclr car-reg))))

Here's a dead simple version of FMkik, with all the parameters tuned to a sensible defaults.

(define (fmkik-default t ft)
   (paramf 60)
   (paramf 1)
   (paramf 1)
   (paramf 3)
   (paramf 2)
   (paramf 0.01)
   (paramf 0.1)
   (paramf 0.09)

A little demo:

(monolith:load "ugens.scm")


(define (run)
  (display "FMKik Demo")
  (regset (gen_sine (ftnew 8192)) 0)
   (lambda () (metro 1))
   (lambda () (regget 0)))
  (mul zz 0.5)
  (out zz)
  (regclr 0))