| Hi:
See prior email for comments. I am pasting the orchestra and score into
the email, for those people who can't read attachments. Lots of
reformatting will need to be done to get these to work, as the email
program will probably put carriage returns in between the coefficients
for the filters.
Sean Costello
; frequencyshifter.orc
;
; Sean Costello
; costello@seanet.com
; March 24, 1999
;
; An implementation of single-sideband (SSB) amplitude modulation.
; Essentially similar to the Bode/Moog implementation, but using
; an FIR Hilbert transformer to obtain the 90 degree phase shift,
; as opposed to the allpass phase differencing network ("Dome filter")
; used by Bode and Moog. The drawback of the FIR approach is that
; the output is delayed with regards to the input, but in this
; implementation the delay is relatively minor (100 samples, or
; about 2.3 milliseconds).
sr = 44100 ; Hilbert transformer designed to work at 44100.
kr = 4410
ksmps = 10
nchnls = 2
instr 1 ; Frequency Shifter, Attempt #4
idur = p3
ibegshift = p4 ; Initial amount of frequency shift. Can be positive or
negative number.
iendshift = p5 ; Final amount of frequency shift. Can be positive or
negative number.
; I use a simple linear envelope to control frequency shift. Can be
modified to be
; controlled by an oscillator, random signals, another signal, etc.
kfreq linseg ibegshift, idur, iendshift
; I use soundin for my input, but any input should work. My particular
test file was a John
; Fahey sample, but I also used a simple sine oscillator during the
testing of the
; orchestra in order to test how much of the unwanted band was
rejected. You might want to
; try running signals generated by pluck through the frequency shifter,
in order to
; get drum-like sounds, as the frequency shifter will "detune" the
harmonic partials
; generated by pluck. Voice works great, too.
ain soundin "C:\\Csound\\Waves\\despair.wav", 0
; Gain has to be adjusted to compensate for loss of the FIR Hilbert
Transformer.
ain2 = ain / 1.570796327
; First part of a 201 sample length FIR Hilbert Transformer. I found
that the longer the Hilbert
; transformer, the better, as you obtained more accuracy throughout the
frequency range. With lower
; order Hilbert transformers, you get less rejection of the unwanted
passband, due to the
; Hilbert transformer not covering the entire frequency range accurately
(there is unacceptable
; rolloff at low and high frequencies). A 201-tap Hilbert transformer
works nicely, with quite
; acceptable rejection of the unwanted passband. I am using filter2 to
implement the transformer,
; as per the recommendation of Jens Groh. Coefficients obtained from
; http://www.cs.york.ac.uk/~fisher/mkfilter/ (thanks to Roger Klaveness
for the pointer).
afilt1 filter2 ain2, 48, 0, +0.0000000000, +0.0008103736,
+0.0000000000, +0.0008457886, +0.0000000000, +0.0009017196,
+0.0000000000, +0.0009793364, +0.0000000000, +0.0010798341,
+0.0000000000, +0.0012044365, +0.0000000000, +0.0013544008,
+0.0000000000, +0.0015310235, +0.0000000000, +0.0017356466,
+0.0000000000, +0.0019696659, +0.0000000000, +0.0022345404,
+0.0000000000, +0.0025318040, +0.0000000000, +0.0028630784,
+0.0000000000, +0.0032300896, +0.0000000000, +0.0036346867,
+0.0000000000, +0.0040788644, +0.0000000000, +0.0045647903,
+0.0000000000, +0.0050948365, +0.0000000000, +0.0056716186,
+0.0000000000, +0.0062980419, +0.0000000000, +0.0069773575,
+0.0000000000, +0.0077132300, +0.0000000000, +0.0085098208,
+0.0000000000, +0.0093718901
; Unfortunately, filter2 can only accept 50 coefficients for an FIR
filter. I came up with a bit
; of a kludgy solution, but it works well: Seperate the Hilbert
transformer into several FIR
; filters, and delay the additional FIR filters by the amount that they
would be delayed if
; they were in one continuous filter, then add together the results.
For example, afilt2 would
; originally be taps #49-96 in the Hilbert transformer, so the output of
afilt2 is run through
; a delay set to 49 samples.
afilt2 filter2 ain2, 48, 0, +0.0000000000, +0.0103049226,
+0.0000000000, +0.0113152847, +0.0000000000, +0.0124104218,
+0.0000000000, +0.0135991079, +0.0000000000, +0.0148917649,
+0.0000000000, +0.0163008758, +0.0000000000, +0.0178415242,
+0.0000000000, +0.0195321089, +0.0000000000, +0.0213953037,
+0.0000000000, +0.0234593652, +0.0000000000, +0.0257599469,
+0.0000000000, +0.0283426636, +0.0000000000, +0.0312667947,
+0.0000000000, +0.0346107648, +0.0000000000, +0.0384804823,
+0.0000000000, +0.0430224431, +0.0000000000, +0.0484451086,
+0.0000000000, +0.0550553725, +0.0000000000, +0.0633242001,
+0.0000000000, +0.0740128560, +0.0000000000, +0.0884368322,
+0.0000000000, +0.1090816773, +0.0000000000, +0.1412745301,
+0.0000000000, +0.1988673273
; Delay for afilt2.
adel2 delay afilt2, 49/sr
; See above for explanation of afilt3, afilt4, afilt5, and adel3, adel4,
adel5
afilt3 filter2 ain2, 48, 0, +0.0000000000, +0.3326528346,
+0.0000000000, +0.9997730178, +0.0000000000, -0.9997730178,
+0.0000000000, -0.3326528346, +0.0000000000, -0.1988673273,
+0.0000000000, -0.1412745301, +0.0000000000, -0.1090816773,
+0.0000000000, -0.0884368322, +0.0000000000, -0.0740128560,
+0.0000000000, -0.0633242001, +0.0000000000, -0.0550553725,
+0.0000000000, -0.0484451086, +0.0000000000, -0.0430224431,
+0.0000000000, -0.0384804823, +0.0000000000, -0.0346107648,
+0.0000000000, -0.0312667947, +0.0000000000, -0.0283426636,
+0.0000000000, -0.0257599469, +0.0000000000, -0.0234593652,
+0.0000000000, -0.0213953037, +0.0000000000, -0.0195321089,
+0.0000000000, -0.0178415242, +0.0000000000, -0.0163008758,
+0.0000000000, -0.0148917649
adel3 delay afilt3, 97/sr
afilt4 filter2 ain2, 48, 0, +0.0000000000, -0.0135991079,
+0.0000000000, -0.0124104218, +0.0000000000, -0.0113152847,
+0.0000000000, -0.0103049226, +0.0000000000, -0.0093718901,
+0.0000000000, -0.0085098208, +0.0000000000, -0.0077132300,
+0.0000000000, -0.0069773575, +0.0000000000, -0.0062980419,
+0.0000000000, -0.0056716186, +0.0000000000, -0.0050948365,
+0.0000000000, -0.0045647903, +0.0000000000, -0.0040788644,
+0.0000000000, -0.0036346867, +0.0000000000, -0.0032300896,
+0.0000000000, -0.0028630784, +0.0000000000, -0.0025318040,
+0.0000000000, -0.0022345404, +0.0000000000, -0.0019696659,
+0.0000000000, -0.0017356466, +0.0000000000, -0.0015310235,
+0.0000000000, -0.0013544008, +0.0000000000, -0.0012044365,
+0.0000000000, -0.0010798341
adel4 delay afilt4, 145/sr
afilt5 filter2 afilt4, 9, 0, +0.0000000000, -0.0009793364,
+0.0000000000, -0.0009017196, +0.0000000000, -0.0008457886,
+0.0000000000, -0.0008103736, +0.0000000000
adel5 delay afilt5, 154/sr
; The complete Hilbert transformer is the sum of afilt1, plus the
delayed outputs of the other filters.
ahilb = afilt1 + adel2 + adel3 + adel4 + adel5
; The original input signal is delayed by the amount of delay found in
the Hilbert transformer.
adelay delay ain, 100/sr
; Generation of sine and cosine signals for frequency shifting
asin oscili 1, kfreq, 1
acos oscili 1, kfreq, 1, .25
; Hilbert transform multiplied by sine modulation signal, while
; delayed input is multiplied by cosine modulation signal.
amod1 = ahilb * asin
amod2 = adelay * acos
aout1 = (amod1 + amod2) * 0.7 ; Upshift output (although this varies on
sign of modulation signal).
aout2 = (amod1 - amod2) * 0.7 ; Downshift output (although this varies
on sign of modulation signal).
; Gains vary with shifting amount, so adjust as needed. Gains of .7
; to .9 should provide unity gain with most settings.
outs aout1, aout1 ; Try small shifting amounts (0-6 Hz), with aout1 in
one channel,
; and aout2 in another. Makes for nice stereo effects.
endin
; frequencyshifter.sco
; Sine table for modulation oscillators
f1 0 16384 10 1
i1 0 30 -50 50
e |