Currently working on
The SwanTester program, for testing the contents of mazes.4th
in version 2017.7.31.0
Consider this release to be a beta version. I've changed quite a lot of internal
stuff and have added some half finished new features. But it's about time for a
new release, and some bugs were fixed … at least.
Error in Divider module, in the pulse mode it would flash the output too often.
Fixed now for the next release.
There was an issue with inserting and deleting 'non-active' modules, like blind
panels and the notes module. Such an action would cause the modules in the editor
patch and the (compiled) synth patch to get out of sync, resulting in the lights
not being updated (and possibly worse). Fixed this to always resync when modules
are being added or deleted even when no structural differences between the the old
and new compiled patch are present.
Pasting text into a display editor (like in the notes module) did not work
properly, as windows on double click on a static text control will fuck the
clipboard. I've changed the way to call up the editor, must use Ctrl+Left Click now instead of a Double Click. It
is also possible to focus the display with a Left Click and
then use Enter. Will need to update some help text too …
k … diddat.
On display editing EndStateChange was not always executed when editing ended,
resulting in the patch no longer being updated correctly on wire edits. Also
resulting in strange behaviour on undo and redo operations. Fixed this. Also there
was a second mechanism locking undo/redo without performing a recompile at end,
possibly resulting in patches no longer being compiled. Removed this mechanism
Added a speed input to the RandSig module. This is a linear FM input, but for the
RandSig module the input value will be clipped to a range [0.0, 1.0] (where a
speed of zero will stop the output from changing and a value of 1.0 will make it
run twice as fast as it would with an unconnected speed input. So it is not
trough–zero for this mdodule.
Made the LifeSeq module rate smart, so it can run at audio rates now.
Sped up the AD and DA conversions as used in the DAC, ADC and Gate modules a bit
by using lookup tables for bit shifts. This also fixed some levels, like the DAC
would output twice as much as it should have. This will change existing patches
making use of the DAC or ADC. It also changes patches using Gate modules with a
bitcount other than one.
Changed some things in the internal working of the code, handling of controls, the
way inputs and outputs are being specified, some control flow trough the program.
This may result in some stuff not working anymore, sorry about that. I will fix it
when I notice it … but having almost 250 mdule types now and various ways
different modules can interact with the patch I may have missed some things in
Added a manual compilation mode to the program. When it is on patch changes will
not result in recompilation, instead they have to be done manually. When this mode
is on you can make changes to the patch without the output going silent, then when
done a manual compile (or leaving manual compilation mode) will effectuate all
changes at once. The keyboard shortcust for this are Ctrl+F12 to toggle the mode and F12 for manual compilation. The help
desk will get cross with me for this one … but, there is some visual
feedback on this in the form of a flashing 'manual compilation' text in the top
pane and also it is made visible in the Action menu. When there are any uncompiled
changes the 'manual compilatin' will flash yellow, and white otherwise. At program
startup the feature will always be switched off (it is not saved in the ini flle).
Knob changes will still change the patch when manual compilation is on – it
only affects rewiring and module insertions / deletions, but this includes loading
a new patch or performing any undo / redo operations.
Anyway, thought this might be useful for live patching, we'll see about that. The
work flow would be to hit Ctrl+F12 to turn the mode on, make
some changes, then hit Ctrl+F12 again to compile the patch and
hear the changes.
Actually this is pretty weird on structural changes, it may cause some unexpected
behaviour. Still, to do a bunch of knob edits, and have them kick in at the same
chosen moment has been useful for me.
I've changed the default behaviour for modules and controls to be enabled for
randomization. Randomization used to be all enabled by default, it's now all
disabled by default. I've also changed the feedback on this, screen items enabled
for randomization are now marked as being special, this used to be the other way
around. (Gabe you were right about this from the beginning, took me some time to
see it, thanks :-))
I've added some control over the randomization range. It is now possible to set a
minimum and a maximum value for randomization on knobs. This can be set by
changing the knob value with Ctrl or Shift being held down wile changing the value (either trough the mouse, the mouse wheel,
the keyboard or by clicking the up / down arrows under the knob). The range, when
not maximal, will be indicated by an arc being painted on the knob's edge (welp
… it doesn't look too pretty right now, but it works) and the selected
range is also visible in the hint popup (when simple hints are not enabled). Ok,
not the best image, but it's the blue hat on the topmost knob … so here is
another one, the hat can be red too, meaning the maximum
is less than the minimum, giving inverse response (not that such matters much for
random signals). It is still possible to navigate the knob outside the set range
manually. I did not implement this on selectors … as of yet … As I'm
not sure how to give visual feedback on it, and also there is an issue with some
of the selectors having dashes in their value list … separators …
those are a bit of a PITA. I did implement it for the simple knobs not having a
knob at all but jsut the up / down arrows. Here the results will be visible in the
popup hint only.
Made a multi–sine oscillator, which generates six sines with individually
settable amplitudes and frequencies individually settable relative to the main
tuning. The amplitudes can be modulated by an external signal. The chain input is
summed with the oscillators into the output. There are mutes for each sine
individually and on the resulting output as well. The sync input when going active
resets the phase to zero for all the oscillators. The main tuning has exponential
FM modulation and a separate frequency fine tuning. Id did not find room to
include PM, but each oscillator has a separate AM modulation input.
Made a text writer module which can be used to write text into a file. I use this
to couple a radio stream title to a patch, such that when I change the patch the
stream title will be updated automatically. It can hold multiple lines of text,
and sending out the next text is controlled from a trigger input. When the module
does not get triggered it will statically output the first text line. The text
file will only be updated when a new line of text gets selected. This happens at
patch load time, patch reset or when a trigger comes in and there is more than one
line of text. When the file does not exist it will be created, and when such fails
nothing bad should happen.
Made a stereo version of the cubic clipper. It treats both channels
independently but with the same parameters, as if there are two clippers set up
with the same alpha and hysteresis values.
This module will step trough recorded automation snapshots, this can be complete
snapshots or recorded single value changes. The control can loop once it reaches
the end, and it can be made to play in two directions.
I've added value history on knobs, modules and the patch as a whole. This with the
possebility to undo an edit without a recompilation being needed. It is also
possible to make selective undos on the patch by selecting a bunch of individual
items in the list. This works on the patch level only, for the control and module
undo only one item can be selected from a popup menu. See the images below.
With this I've also split the undo history up into two separate histories. A
history for structural changes (those can be undone and redone with
Ctrl+Z and Ctrl+Y) and this new 'value
history', which can no longer be undone/redone with Ctrl+Z and
Ctrl+Y. The control history, on undo, will not silence the
patch while a structural undo / redo does need patch recompilation, which will
stop audio briefly.
Also this causes automated changes (like randomization, morphing etc.) on the
patch to not be recorded in an undo history anymore. Which also causes live
morphing to no longer mess up the undo history, it is just not being recorded
anymore. (but you can still make snapshots for the automation recorder.)
Still working on a method to let cable changes not cause silence, as those would
not really be needed (a cable change results in some pointers being changed only).
And while at it, I've also made an event recorder. In its current state it can
only be used to play back snapshots, timed playback is not working yet. With the
new AutomationStep module described above this can be controlled. I'm working on
more features, and also working on keeping things consistent when modules are
added or removed from the patch (it's all a bit messy still, trying ideas mostly).
See image below, and the mini version of it on the left.
There is no automatic Save and Load currently, but the automation control screen
has a load and a save button. Automation is saved into a separate file with the
same name the patch jas file has and an .automation extension, on load it will be
checked if it matches the patch it was generated on.
Another thing I'm working on is an abstraction editor. It is possible to make
details of a patch public, the abstraction editor will pick up all the publics and
generate a module from that with the publics at odd positions, but stuff can be
edited. This is even more just in the 'gathering ideas' phase. Anyway, I'll not
disable it for a release even whn it is not very useful currently. See image
There is no automatic load and save for abstractions, but there is a Load and a
Save button in the abstraction editor. Abstractions are saved in a file with the
same name as the patch it was generated from using .abstract for the file
extension. On load it will be checked if the abstraction matches the currently
Added a 'unique ID' (GUID) to patches to keep track of mappings between patches,
automation and abstractions. These should not be to easily tracable to the
computer which generated them … when I can believe the µSoft docs on
this. Anyways, you can always strip them out, the patch will still load.
The GUID will not change during the lifetime of a patch, not even when structural
changes are being made. This means that the sync between patches, automation and
abstraction may still get fukt. At least its not possible to load abstractions and
automations on a patch it was never based upon.
I'm trying to make it so that when a patch is being change structurally and an
abstraction or automation is loaded for it that these will be updated in a
sensible manner. (And eventually such would mean automatic save / load will be
needed on abstraction and automation files (or tht they get stored into the patch
itself).) Anyways … for now, you will loose somme work probably while
working with the new features.
Single items can be reached (and be undone) trough the control popup menu.
Single items can be reached (and be undone) trough the module popup menu.
Multiple items may be selected to set them to the value present in the 'Prev. value'
The knob on the highlighted module marked in green is the currently selected
control, the one to which the graph applies. In the patch mod 1 is the player,
allowing for snapshots to be played in a clocked manner (not respecting the time
they were made on). So his acts as a sequencer, basically. A click on the send
button will send a whole column of values back into the editor. The Clear button is
destructive, it removes all recorded events. Points in the graph can be moved
around, when moved in value only the value will change for that step, when moved in
time a new time steop will be added. I'm working on more functionality.
Items marked in black are made public, the green item is the currently selected on
in the editor for which properties can be changed. This is a toy for now to gather
in version 2017.5.21.0
There is an issue with the Seq16 module in that it will sometimes not run due to
the number of steps being seen as zero, I've fixed this. Meanwhile a workaround is
to press F7 or F12 to make the sequencer run again.
There was still a race condition in the PulseSync module, solved now. A negative
edge on the sync input would clear the internal state, but the incoming pulse
might not have been processed yet (in case of a long sync pulse time). Made a
counter now which will clear the internal state and the output after a fixed
number of cycles, and in case the pulse input had gone active again within that
time it will just be armed anew.
Changed the module order on the Control tab to have all scaling modules grouped on
the left side.
Upped the maximum count values for the triggerable oscillators and LFOs. This will
change existing patches using these modules.
Added Hold mode on EnvAHD module. When on it prevents the module from going into
Release as long as the trig input is still active. When off the module works as it
Added an active output to the LfoTrig modules. This differs from the inverse of
the ready output in that ready will never be active before the first cycle ran
(and the module will not run then yet when it saw no trigger signal).
Added some swell control to the EnvAHD module. Swell when active will cause a rise
during the hold phase of the envelope. The amount of the effect can be preset and
modulated, and the shape can be selected. The time for the swell is the current
hold time. The envelope graph more or less shows the effect of this new control.
Added swell to the EnvADSR module as well. It works a bit different here, the
swell time is taken from the release time instead of the decay time (as there is
no hold time to be set). Also setting a large amount of swell will reduce the
attack level by up to one third.
With swell set to zero the modules behave as they did before. For shape
impressions see the image below.
Added a freq (unattenuated FM) input to the HrastOsc, also added shape and morph
modulation on it.
I've changed the sensitivity of all speed inputs on LFOs and oscillators. They
will run twice as fast as normal now with an input signal of 1. A zero input
signal will make them stop, and with negative values they will run backwards. Of
course the only wave shape changing on that will be the saw wave. This will change
the behavior of some existing patches.
The phase modulation on oscillators and LFOs was changed to something more
correct (for large phase modulation values), turned out to be a tad cheaper as
For the following modules I've changed the range of the slew control to make it
more useful: TypeFlip, SeqChord, Slew and SeqRandVal. This will change existing
patches making use of the slew control on these modules, however when slew was off
on them it will still be off for the new control range. Also it is still possible
to fully freeze changes with the control turned hard right.
Added 'function modulation' to the Gate module. The blue input when going from
zero to one will go trough the eight selectable logic functions (it is being used
as an offset (modulo 8) on the value from the Gate type selector).
Renamed the Pulser module into Wavolver – as it was really that …
and then made it work properly. The renaming will break existing patches using
this module, the module will still be loaded but all connections to it will be
lost. But then again, the name was plainly wrong, and it did not function
properly either. The actual pulser thing can be done now with the triggered
oscillators, I've added pulse count modulation to those. These are all variations
on VOSIM of course.
Added a new display mode to the Quantizer module. It used to show fractions of
notes, it can now show fractions too. Not that this changes anything on it's
workings, but with the mode set to Fractions it is easier to understand how it
works for linear control of (low frequency) oscillators. For instance (see
illustration), when the fraction is 1/4 and the rounding type set to 'round' and
the output is used for speed control of an LFO the LFO will run at n/4 of it's set
speed (for n = 0 to 4 assuming an input ranges of 0 to 1, and assuming the linear
frequency control is being used (called speed in most places)). I've added the
same option for the built-in quantizer in the SeqRandVal module.
I've added different rounding types for the internal calculation. The module did
use the Round method before, but it can now also use Flooring and Ceiling. The
default still being Rounding. The illustration shows the quantizer set to 1/4 with
from top to bottom the input signal, the floored quantized value, the rounded one
and the one using ceiling. This option has not been added for the SeqRandVal
module, that one will always round.
Changed the Song module to have active 'end' and 'silence' outputs at patch
startup and after reset (both global and module specific), they used to be
inactive then. This makes it easier to use a PulseSync module on the 'end' and
'silence' outputs. This may break some patches that are making use of these
outputs, but not likely so.
Added a signal shaping module, it can transform a linear input signal into an
envelope shape type output signal with inversions and signal types being applied.
The module is rate smart, so it can be used for audio signals as well (but there
will be some aliasing). For shape impressions see the graph below.
Added yet another scaling module, the PropScaler. This one has a modulatable
parameter p which controls the in to out transfer as:
out = in * ( p - 1) + p.
This replaces a set of four modules that would otherwise be needed to make the
same functionality. Effectively p sets a lower limit on the output value and the
input range is proportionally distributed over the remaining output range.
Added a new sine oscillator with more modulation control than the other
oscillators have. It has amplitude modulation, phase modulation, linear FM
modulation (trough zero), exponential FM modulation and in addition the frequency
fine tune can be modulated trough the ct input. The sync input is a hard sync.
when it goes active the internal Phase accumulator is reset to zero.
This is after an idea by Ian Fritz. The analog xor makes it's output active
only when the sum of the input signals is over the set set Threshold value, but
below 0.5. The threshold can be set from -1 to +0.5, and it can be modulated
trough the T mod input.
Envelope shape impressions
Shaper shape impessions
in version 2017.4.22.0
Moogfilter could produce denormals - added some guards there. Also optimized the
filter a bit (20% off from the execution time), but it still uses an awful lot of
cycles – more than a reverb does – I don't really understand why that
Compressor could produce denormals - added some guards there. Pluck module idem.
Graph Image for S shaped attack on the ADSR envelope module was wrong, fixed it.
Made the S attack and decay modes working on the Seq16 module, they acted like exp
Added code for trying to get some better idea as to why PortAudio initialization
failed. It will report failures to the logs.
Added an off-beat output to the EuclideanRhythm module, it is active whenever the
regular output is not (and the clock is active). Basically it runs the reverse
pattern of the regular output.
Added an invert input to the Seq16 and the Sequencer modules. In invert mode the
sequence is put upside down.
Added inputs to the Switches4 module. When these are not connected it will behave
as it used to. And when they are connected they will be switched to the outputs.
Added range modulation to NoteQuantizer, ScaleQuantizer and ModQuantizer modules.
Added tanh( x) function to the Monadic module.
Added chain inputs to the TransInv module, these are just added to the calculated
Made the pulse delay module rate smart – however – the shown times are
eight times as short when the module runs at audio rates (this is being indicated
in the displays). Also made the MultiCompare module rate smart, so that now all
the logic modules can switch to audio rate computation.
Added some values to the MConst module to make it usable for controlling note
intervals. uni (0), mi 2nd (1), 2nd (2), mi 3rd (3), ma 3rd (4), 4th (5), dim 5th
(6), 5th (7), mi 6th (8), ma 6th (9), mi 7th (10), ma 7th (11) and octave (12).
These values are TET based and are fixed, even when the main tuning is changed.
Added a sent output to the MIDI CC output module to allow for easier sequence
Added a clear input to the Delay module, when it goes from inactive to active it
sets all the delay memory to zero. This is glitchy, as it was intended to be.
Added input attenuation controls for the Formant and Formant2 modules.
Added a speed input for Osc, Square, MultiOsc, OscTrig and Squaretrig
oscillators. This basically is linear thru zero frequency modulation. When speed
is set to zero these oscillators will stop and they can be used as lookup tables
by controlling them from the pm input. And while at it … also added speed
controls for Lfo, SquareLfo, LfoTrig and SquareLfoTrig modules.
Changed the maximum acceptable input level for the GVerb module to 100, in the
original code this was 1e5 or so and had that lowered to 10 before – but it
could cause distortions that way … so upped it a bit. These are silly
levels, but this can happen when the input level is high and the output levels are
set low to compensate for that. Which would be silly to do probably, but I needed
some more forgiveness there.
Added a 'hold' mode for the EnvAR, EnvARRetrig and EnvConrol modules, when active
they will not enter the release phase as long as the trig input is still active.
Also removed a possible click from these modules ( on the transition from Attack
to Release or Hold mode) and removed some needless calculations … like
subtracting Ln( 1).
Added mode selectors for the FixedDiv and PrimeDiv modules, these can be set to
either Square or Pulse. In Square mode the outputs will all have a 50% duty cycle
and in pulse mode they wil be active for one positive input clock time.
Added a reversed mode for the arpeggiator, and added a reverse input for playing
the arpeggio backwards. The reversed mode plays the notes in reversed order of
reception i.e. last note first. Also added a transparent mode, when the
Transparent control is active no arpeggiator actions takes place but instead the
last sampled input value is being output when the output clock goes active (making
the module behave like a sort of a sample and hold module (except that it has two
sample clocks then).
Added a trans(parent) input on the Poetry module. When it is active no poetry
generation takes place but instead the last sampled input value is being output
when the output clock goes active (making the module behave like a sort of a
sample and hold module (except that it has two sample clocks then).
Added count modulation inputs for LfoTrig and SquareLfoTrig modules.
Added a level modulation input for the Quantize module.
Made the control decimation programmable, it can be set from the
Settings Screen [F3]. The default value is 8, what it always had been, but it can
be lower or higher now. Higher values will mean that less processor resources are
being used. Changing the value however also means that some modules will run
faster or slower, this affects some of the blue filter modules i.e. the slew times
may change etc. It is of no concern for the red (audio) filters though.
Working on some MANIAC features …
I've dded cross fade modulation to the Seq16 module and also added a random input.
The random input will set all the faders to random positions. Added three 'canon'
outputs, these are shifted by four steps for each one. So when the first output
outputs step1 the 2nd out sends step 5, etc. This way the sequencer can be used as
a 2 x 8, 3 x 6, 4 x 4, … sequencer, but it is also possible for instance to
set like 12 steps and use output 1 and 3 and then they will have eight sliders
overlapped and four unique ones for for themselves. The xfade works on all four
outputs, but there is still just one chain input which is being added to all four
outputs. Added a 'hold' input, which when active will hold the last sequencer
output value and it will also block the chain outputs from being updated, but it
keeps the sequencer running. Then added skip inputs for each step, when a skip
input is active that step will not be used (making the sequence a step shorter).
Added a clockskip input too, when it is active the sequencer will freeze at its
current step. This is different from the Active input in that the Active input
outputs no step values but passes on the chain outputs only. When a clock is being
skipped the current step and output values will be he held and the chain inputs
are no longer sampled. Then I went on and made 16 step outputs, going active when
the step is active and the incoming clock is high or the trigger mode is set to
(G)ate. Oh, and also added a TimeWarp (tw) output, which can be used to control
the speed of the driving clock, it is meant to drive the speed input of an LFO.
The idea is that when steps are being skipped the sequence length can be kept the
same when using the TimeWarp output in this manner.
Getting closer to the M.A.N.I.A.C.
Added the 'canon' outputs on the LUT module as well. Added a 'steps' control as
well to map a zero to one signal range on the the set number of steps, step count
can also be modulated. Then added a random input for doing fader shaking too. With
a negative step count (which can be set trough the steps modulation input) the
unit will run 'backwards' – that is – for larger selection values it
will move to a lower step value. Note that with fewer steps and a ramp on the
input there will be less steps in the same time, so when used as a sequencer the
sequence will run slower then. Added 16 step outputs here too, there is no clock
or active input on this module, so the step outs are active for the whole time the
step is active.
Added a DC blocking module with a -3dB point that can be set from approximately
20 ~ 40 Hz to 400 ~ 800 Hz in audio rate (red, depending on sample rate) mode and
from 2.5 ~ 5 Hz to 50 ~ 100 Hz in control rate (blue, depending on sample rate)
mode. The further the knob is turned right the higher the cutoff frequency will
be. DC will always be totally blocked no matter what value the cutoff is set to.
Feedback delay lines (and there are a couple of other modules that do not like DC
very much) can lock up when there is DC present in the loop, this module can be
used to get rid of the DC, probably best before the loop and not inside it.
Added a MIDI Program Change Output module, also featuring a sent output for
easy command sequencing. It will send out a a program change message when the gate
goes active or when the program is manually changed. The actual program is the SUM
of the values read from the prg control and the progr input. A change on the progr
input will not trigger a message to be sent – a gate signal is needed then.
Added a MIDI Parameter Number Output module. This module can send both RPN and
NRPN data and it can do so with the most significant septet only or it can send
both data septets. Added the chain output to this one as well. Data will only be
sent when the gate signal goes active.
Changed the compressor looks a bit. The LED scale was not very informative (as the
scale is pretty large things barely moved, and there was no feedback on actual
gain either) so … removed it, but added a dB value indicator showing the
Also added a side chain input and output. Effectively this is a 3rd compression
channel where the compression is being calculated on either the side chain channel
(side mode) or on the stereo signal channel pair (norm(al) mode). So it is also
possible to side-chain a mono signal from the stereo inputs.
Then added a DC blocker on the inputs as in RMS mode DC on the inputs can do some
weird stuff. The blocking can be switched between AC and DC. AC mode has a -3dB
cutoff point at approximately 20 ~ 40Hz (depending on the sample rate) and DC mode
does nothing, The filter will only operate in the compression calculation chain,
the signal chain is not being filtered.
Added a PulseSync module. The module gets triggered by an incoming positive edge
on the pulse input, which it will then hold internally. When a subsequent positive
edge appears on the sync input the output will be set active. Once the pulse got
processed the output and the internal state are both being cleared when a negative
edge is seen on the sync input. The incoming pulse is guaranteed to never get
This module can be used to sync up a pulse event appearing at a random time to a
syncing clock signal.
Added a Transpose module. Four separate transposition amounts can be set each
having an activation input. The output will be the input note value transposed
over the sum of the active transpositions. Transposition range is -24 to +24
Added a SquareSineLfo module, it outputs a sine along with a PWM controlled square
wave. I often end up clocking things with sine LFOs as sine are easy to multiply
up to higher frequencies (using the ChebGen module) which is easier often than
starting with a higher clock and dividing it down. Also the sine shape is more
useful to do (synced) modulations with. However its not easy to change the 'pulse
width' of the sine, so that is what the square PWM is for, that one is easy to
make changing note lengths for driving sequencer.
Made a PulseSkip module. It will pass on input trigger signals only when the input
level is larger than the compare level. Levels are computed as the sum of the
preset level (as made visible in the displays) and the modulation level. Once a
pulse got started will only be ended when the trig input goes inactive, so either
a complete pulse is being passed on or it is being skipped.
in version 2017.3.14.0
Bug in DataGraph module for the splines mode, it outputs X values instead of Y
values. Using Y works way better - so that is fixed now. And its not in the
AudioGraph module, as that one can not use splines – pwew :-)
Mode and range changes through selectors were not handled when controlled with the
keyboard (only mouse clicks worked for that), fixed it.
Added an 'act' input for the EuclideanRhythm, SeqRandom, SeqRandVal, Pattern and
Added inv outputs on EnvAHD and EnvADSR modules, they output 1.0 minus the value
that is on the env output.
Made a controller module for the DataGraph module to allow it to do envelopes. The
help blurp says : A retriggerable envelope controller. The envelope will start
when the trig input goes from zero, or below zero, to above zero. The output will
then in the set Attack time go to the level set with the level control. When the
trig input falls off the output will start getting larger again for the set
Release time, till a value of 1 is reached. At every new trig start the output
value is reset to 0, and the above cycle will restart. Both the Attack and Decay
phase are linear, any non linearity is to be set in the controlled graph. This
module is meant to control the GraphControl module, the actual envelope shape is
then drawn in that module. The set level will then correspond to the vertical
distance in the graph where the hold value will be.
Made a pattern sequencer module to be used for drum patterns. When set at low
speed it can also be used to control the time structure for a self playing patch.
A full pattern is made from eight parts, where each part is composed of eight
sections and each section has eight elements. This makes for a total of 512 steps,
where each step controls 24 bit outputs simultaneously. The steps can be set to
off, to pass the incoming clock, or to be on.
For detail information please click on the module, or for some background
information have a look at the forum
Sequences can be saved to disk and reloaded just like any module (or any group of
modules) can - as a preset. Right click on the module and select load / save
preset from the context.
in version 2017.2.25.0
Range control for the pulses module was not working, fixed that.
Output signal type selection for the pulse delay module was not working, fixed
that. Also tried to clarify the help text a bit.
Constant module when put into 'note' mode is off. And this seems to be wrong in
more module types. Indeed it did affect the Constant, LUT and Knobs4 modules and
it is fixed now. Also made it so that when 'notes' mode is selected the note
controls have 128 steps now, and possibly some other number in the other modes.
Also the LUT module was having an offset in the 'notes' mode, this got fixed too.
These changes will affect old patches using any of these modules in 'notes' mode.
Made a Moog style 24 dB low pass filter.
Inspiration came from here, the
Huovilainen variation on the theme. I've found it to be a bit explosive …
the volume that is, so made it to oversample a bit more and also added a
saturation function (tanh) on the output, as it had a tendency to go like very
loud when resonating. This is not a cheap filter CPU wise, but I think it to be a
nice one with the built-in distortions. On the referenced web site there are some
more variations, I may try some other and make a selector maybe for different
Made a fixed divider module.
The module has a series of outputs with fixed division rates. After
reset all the outputs will be off, to be toggled each time the number of input
clock periods matches the division count for that output. The output will stay
high for one clock period then.
Made a multiple waveform oscillator.
This module simultaneously makes a sine-, a
trianglar-, a saw- and a square-waveform. The PWM input provides linear Pulse
Width Modulation (on the square output only).
in version 2017.2.19.0
Delaytime range on stereo looper was not working, fixed now. Also changed the
start and length control modulation amount knobs to be displayed as linear (they
were actually working as linear controls already but not displayed as such).
Some screen painting took place on the desktop's device context, changed that to
happen on the editor's context only. This draws better selection rectangles and
better lines (on cable drawing). This may as well solve an issue with the screen
not being repainted properly (which was reported by someone using Windows 10). Also
thickened up the lines a bit for better visibility.
Added inv outputs on EnvAR and EnvARRetrig modules, they output 1.0 minus the
value that is on the env output.
MIDI transmit bug. The command was never sent only the data bytes … Fixed
now. And of course I had forgotten to test some code …
Added f(x) = - x and f(x) = 1 - x functions to the Monadic module.
Added a a modulation depth control module
. The graph illustrates it's workings
(where the red signal is the wanted modulation depth (mod), the green signal is
the modulation (in) and the blue signal represents the resulting output).
For the inputs and the output the signal type can be set, for the graph they were
set as in the module image. The mod signal and the output being unipolar and the
modulation (in) signal being bipolar. I've made this module primarily for AM
modulation (tremolo), but it would work for vibrato as well when applied to a PM
input of an oscillator.
The internal calculation used is : out = mod * ( in - 1) + 1, so that when mod = 0
the output will be 1 and when mod = 1 the output will be a copy of the in signal.
This is being calculated on signals assumed to be positive only (unipolar), the
input output type selectors are to be used to ensure such scaling.
in version 2017.1.29.0
When windows screen magnification is set to something else than 100% everything on
screen gets messed up. Turned off screen scaling, which paradoxically results in
better scaling - I guess the scaling property on forms is a promise to windows ...
anyways, windows will now scale all stuff properly - or so it seems.
Bug in LifeSeq module, the chain input does not work – fixed now.
Obscure bug in the wave file reader code, it would read more samples than present
in the audio file which would cause glitches on playback. Fixed now.
Some of the 6 dB filters (the high pass parts) could produce denormals, fixed
Bug in multiplier module where the leftmost input would not work due to having a
wrong name. Fixed that, but all patches using that input were not working properly
and on reload will not restore the connection. When needed this can be fixed
manually. Open the patch in a text editor, search for all occurences of the text
'multiplier_in47' and replace all of them by 'multiplier_in7', the patch would
then load again as intended.
Bug on pasting modules. It looks like when a selection larger than what is
present in the current patch can not be pasted. This has to do with an internal
naming conflict for modules. This issue must have been present for years I think,
looking into it now. Is fixed now, it made the code somewhat simpler too :-)
Added a reverse input to the LifeSeq module, when active it plays from right to
left. Also added stops to the module. When one stop is set it will play from the
first column up to the row where the stop is set and it will then jump back. When
two stops are set it will start in the column after the leftmost and it ends in
the column just before the rightmost. When the reverse input is active this gets
reversed. When no stops are selected the full range will be used. On reset the
cursor will jump to the column after the leftmost stop, unless only one stop is
set – in that case it will go to the first column. This also gets reversed
when reverse mode is active. I thinks the stops to be interesting mainly for the
Changed MIDI NoteOn handling a bit. When a NoteOn with velocity 0 is received it
gets translated into a NoteOff event. The velocity for the generated NoteOff was
set to zero, it is now set to 64 instead. Changed that for the MIDI file player
Implemented running status for the MIDI transmitter, this was already present for
Updated the MIDI decoder and encoder to be able to handle RPN and NRPN data, so
could make modules handling those MIDI messages now. Implemented a mode for this.
When 7 bits mode is on the callback will be called when the MSB comes in, in 14
bit mode the callback will be delayed until the LSB comes in. When MSB and LSB get
swapped by the sender it will still work, provided 7 bit mode is selected, as in
7 bit mode LSB reception will not trigger the callback (and the internal value
gets updated anyway on both MSB and LSB reception.
Data increment and decrement are implemented as well, in 7 bit mode they will
change with steps of size 128 and in 14 bit mode with steps of size 1. Increments
and decrements are clipped to the range [0 .. 16383] (which may get interpreted as
a range [-8192 .. 8191] depending on the actual receiver), no wrapping takes
place – could make a mode for that too though I guess.
All this is in preparation for MPE (Multidimensional Polyphonic Expression)
… going to be some messy fun that for what's basically a mono synth
… sorry paraphonic :-)
But first MIDI will need little more attention.
For PortAudio I've changed the way buffering is handled. It is now possible to set
buffer size of zero, whech means that PortAudio decides on it. This works for ASIO
as well. For legacy mode this is not possible, a 4096 byte buffer will be used in
legacy mode when 0 was set. I've noticed that the WASAPI interface gives me best
results for latency, but I've also noticed that I'll have to shave off some of the
peak load for some of the modules to be able to use that for larger patches. I've
added a buffersize display under the CPU load display to be able to see what gets
actually being used (it shows the number of samples delivered and requested by the
PortAudio callback). Setting the buffer size to zero may cause the VU meters of
the main window to be updated a tad irregular, but didn't actually really see
that. Also, in the Debug Screen [F5] I've added latency indicators, they show what
is being reported by PortAudio.
Processing for the LifeSeq module is spread a bit better over time now. After a
change request was seen a column counter is set up which gets adjusted on every
control rate tick. On each tick only one column of the automaton gets updated. As
a consequence the updates should not occur any faster than once every 32 control
rate ticks (SampleRate / ( 8 * 32) Hz). Also the display will now get updated only
when there was a change.
Made it so that all MIDI sends from a patch on a channel > 16 are sent back into
the patch itself (and the channel is decremented by 16 then). This makes it
possible for a patch to send MIDI data to itself by allowing it to send on a
channel > 16. For the MIDI send modules these channels can be selected as ic 1 to
ic 16 (ic standing for Internal Channel). The MidiNoteOut and MidiCCOut modules
now allow for such channels to be selected, so a patch can now send notes and CC
messages to itself. Such MIDI messages will be handled internally in the synth
patch and will not be visible outside it (like in the user interface, or in the
outgoing MIDI stream).
Two new modules, a Phasor
and a painted waveform thingie, the AudioGraph module
The Phasor was created to control the AudioGraph, but it can also do phase control
The AudioGraph is better suitable than the DataGraph module for audio rates as it
internally uses Differentiated Parabolic Waves to reduce the aliasing a bit.
I've added an auto scaling feature which after every data alteration rescales the
graph to use the full Y value range. This feature can be turned on or off.
Also added an input to randomize the graph, randomization will occur when the
random input goes from zero or lower to something greater than zero. The actual
momentary value at that stage is used to control the amount of random to be
applied. Small amounts (near zero) of random cause the graph to be changed just a
bit, a value of one would create a totally uncorrelated new graph. Unfortunately
the rnd input acts sluggish … maybe something to fix later on.
Added a tilt filter from here.
center frequency can be set for it and a tilt factor for the frequency response
line. With tilt in the mid position there will be no filter action, turn it up
for more highs or down for more lows in the output signal. The center frequency is
the point the response line rotates around. The maximum tilt is ± 6dB /
Added a txt end output to the Song module, it will fire when all phonemes are
spoken. It will not fire initially so it can not be used to make the module self
looping. However, the module does have a loop mode for that purpose. I've added it
to be able to only start the module when it was not already running (with an RS
Added hold mode to the Demux module. When active XFade will no longer work and
outputs will keep their value when they get muxed out (integrated sample and
hold). The new button toggles between cross fade and hold modes.
Added a sync output to the RandomWalkLfo module. The sync output goes active when
the output values change and it goes inactive halfway the LFO period. This so I
can get triggers at the LFO rate. Also added an output smoothing mode to this
module. When smoothing is off a stepped wave is produced, when it is on the wave
glides from old to new values. And also added a distance modulation input.
Added a maximum value display to the Value module, it will display the maximum of
the absolute value seen. A reset button was added too to be able to reset the
maximum to zero. Also a patch reset will set the maximum value to zero.
Changed ini file loading a bit, at first Wren will try to load an
inifile based on the name of the actual executable file name. When such does not
succeed it will try to read a file 'wren.ini' from the same folder the executable
is in. This assumes Wren originally will be called 'wren.exe', but
makes it possible to have a copy of the executable under a different name which
will then try to read the original settings (but they will be saved into an ini
file named after the actual executable fiel name). Anyway, this should make it a
bit easier to have two (differently named) Wren executables in the same
folder, and to have the new one to initially inherit the settings of the default
one (they can be set to differ later on). The looks will always be shared.
in version 2016.10.23.0
Oops ... a bug in the AM modulator causing an addressing error, fixed now.
I've changed the implementation for the intdif module a bit. For the integration
function the output value is divided now by the execution rate of the module. This
can be scaled with the gain control slider, but it means the output will be way
lower than it used to be. Likewise for the differentiation function the
output value is multiplied by the execution rate, and this is also scaled with the
gain slider. This results in way more output signal for the
differentiator. Also the output values for both integrator and differentiator are
clipped to a range [-10 .. 10] (this used to be the case for the integrator only).
The execution rate depends on the set sample rate and it can be either control
rate or audio rate depending on the rate of the input signals.
Trying my hands on some Markov stuff. Not sure if I can get the learning mode fast
enough for real time use, playback should not be a problem.
This is a first order implementation.
The internal state consists of a number of nodes each holding some value (for
which a maximum must be set with the max size control), a State variable holding
the current node index (which is not under direct user control) and a matrix of
transition chances (which is not under direct user control).
When the learn input goes active the current input value is looked up in the
nodes, and when found the transition probability from the previous input value to
this new one will be increased with the current strength value (which can be
negative). When the new value was not found it will first be appended to the node
list. When the node list becomes full and the mode is set to 'once' an overflow
condition occurs and the new transition will not be learned (also the Ovfl light
will go on then). When the mode is set to 'cont' no overflows will occur but the
oldest transitions will be discarded instead.
When the 'new output' input goes active the current State variable will move to a
new one, this is a random process controlled by the transition chance matrix.
The state of the module can be saved to and loaded from a file (must still
implement some user interface for that), so … training could be done in
non-real time mode when the need arises. Anyways .. let's test things first
– actually it does not seem to perform so bad, great :-) It will depends on
the input material, when there are many different values things may be worse, but
for discrete events (like note values) it seems all fine.
Now it needs to be made a bit leaky … as currently when the input patterns
change it will take longer and longer before those new patterns will be learned.
Although setting random strength values seems to help here – just like
setting not too many nodes and using 'cont' mode.
Now working on some code to do do the Markov thing a bit more efficient so I can
hopefully implement a second order implementation which is fast enough for
Ok, that seems to work. It also seems to be not too hard to generalize it a bit to
arbitrary orders. I've implemented something, but found no time yet the check the
workings or the the performance.
After a little break and some bug fixes … arbitrary order seems to
basically work, it needs more testing though.
Made a variation of he Average filter with direct frequency control (instead of
just exposing alpha). The set frequency references the - 3dB point. Filter falloff
is 6 dB / Octave, just as for the Average filter. The filter should work on
control and audio rate signals (Rate Smart).
Made a bandpass variation on this and then made a stereo version of that one too.
I've used this one on the final output of a patch to trim off excessive lows and
highs a bit.
When in control rate mode the frequencies are off by the control rate decimation
factor (currently 8), the displayed value being too high. I should fix that by
displaying the lower frequencies, but as of yet there is no proper mechanism for
Added a new tab for generators (gen) and moved some of the 'sequencers' there.
This tab is meant to hold modules to be primarily used for generative music. So
state machines, song generators, cellular automata etc. Moved some modules from
the control tab to the new tab as well.
Automata … well … just one automaton for now, but will likely make a
couple more based on the same underlying engine. This one is a rhythm generator
This module implements an 'elementary cellular automaton'. Each cell can have a
value of either zero or one. Three cells are evaluated according to the set rule
and this will yield a new value for a next generation cell. The rule number [0 ..
255] is being interpreted as a bit pattern which is indexed by the three bit
pattern generated from the three evaluated cells. This is all according to
Wolfram's theory about elementary cellular automata. The start state of the
automaton consists of one single cell having a value of one.
With the steps parameter you can set the number generations to be calculated, this
results in a bit string. On every step a next bit will be sent to the output and
when the end of the string is reached the sequence will wrap back to the beginning.
The Faults parameter sets the average number of cell faults generated for each new
cell calculated. The set number is divided by 10,000.
The total length of the generated pattern increases with two on each new evaluated
step, which results in length = 2 * steps + 1, which is odd always. The reset
input can be used to wrap back sooner.
The blue output has a weighted sum of the last three bits ( Bit[ anIndex] + ( Bit[
anIndex - 1] shl 1) + ( Bit[ anIndex - 2] shl 2)) / 8.0. The dir input when active
reverses the play direction.
Some rules will not generate any output at all (like rule 0 or 255), some will
generate simple repeating patterns and others will be almost random. For some
rules the steps setting may not change the sequence much, for others a next step
may differ wildly from the previous one.
For some ideas about possibly interesting rules have a look at my rules page. At
some stage I may build some of the visuals into Wren , but not at this
stage. That page, at the very end, also shows an implementation of the algorithm
And another cellular automaton based module. This one uses Conway's game of life.
the current help text says (subject to change though):
A Life based sequencer.
Based on Conway's game of Life, but there are some extra modes selectable from the
mode selector. The step input moves the cursor, which will put the cell values
from the current column on the green outputs. The change input triggers a new
generation of live cells, according to the currently selected rule. The blue sum
output has the column sum of the cells under the cursor, this can be a binary sum
or a linear one. The grid can be set to be wrapped or unwrapped. In wrapped mode
the top connects to the bottom and the left side to the right. The fault rate
parameter determines the amount of faults made in applying the evolution rule.
When the number of cells drops below the low count the grid will be filed with
random values, the chance of a cell becoming alive is set with the rnd amt
parameter. The rnd button will fill the grid with a random pattern, obeying the
rnd amt setting. The clr button will clear the grid, this usually will then
immediatly set random pattern as the live cell count drops below the minimum. It
is possible to draw on the grid, a single click will toggle the cell state, with
shift cells can be turned on and using ctrl instead will turn cells off.
Using a right click on the grid the current state can be saved to or loaded from a
This a a pretty big module, and 32 rows seems a bit much maybe, but I've found the
game of life to be more interesting on larger grids. The current 32 by 32 size
seemed a minimum for interesting patterns to occur. And at the same time 32 logic
outputs seems like overkill as well, for the sum output it's a nice amount though
(2.5 octaves in the note modes).
Made an inhibit control on the change input to be able to stop rule evaluation,
and also made a 'Freeze' mode (in addition to the various ;ife modes) in which the
current pattern will not change – this allows for painting sequences.
Now if only I could get the module to load itself from a patch file … it
would then double as a 32 x 32 (event) sequencer (the sum output can be set to
make note values though) … it also reinitializes on every module insertion
or deletion … which it should not do. But otherwise it seems to work well.
Ok, the save and load stuff works too now, but the mode has to be set to 'Freeze'
for this to work properly (or else the internal Life machine will have it's own
ideas about the pattern).
The new grid control thingie could be nice for other modules as well :-)
When Wren is closed the current patch will be saved in the
application's home directory (where wren.ex resides) as
'__l__a__t__e__s__t__.wren'. This file can be reloaded from the file menu trough
the 'Load last patch' item. For just in case … This is not saved in the
most recently used patch list (unless you manually open it; it will not be opened
automatically on Wren startup).
in version 2016.10.2.0
Added the Markov module, but it has not been fully tested yet, see remarks in the
'working on' section above. Also I did not implement the code for saving and
loading models yet – or rather – I did, and then the code changed, so
it needs to be done anew.
Delay module, in 'short' mode, does not get correctly initialized on patch load,
it seems fine on patch recompilation though.
Or actually … several parameters were not updated in the synth after for
instance a range change on a mixer or when clicking an rnd button on a sequencer,
etc. etc. Fixed that, it was introduced with the randomization features in the
last couple of previous releases.
Made some new noise modules with Perlin like noise, in which the roughness can be
controlled and the pattern length. A clocked one and a free running one. New noise
values can be inserted to change the pattern. The maximum pattern length is 4096,
the length controls set a fraction of that. The number of layers can be set, more
layers give more smoothness, at the expense of processing time. The new input when
unconnected is active, giving noise like behavior, when it is set inactive the
behavior is tone like. When made active less frequently it will change the timbre.
I'll probably make LFO versions for this too, welp, would like to at this time, it
seems like a slowly clocked one can make nice percussion patterns. Also I'd like
modulation of the length – ok, added that. Not sure how strictly Perlin this
is, I've tweaked the interpolation function from one layer to the next to more or
less give the same amplitude for smooth and rough settinging (but it is random of
With the above … there now are 200 module types.
And then when on the Perlin you do not set new values very often it makes sense to
have frequency control as well. The maximum sequence length was set a bit shorter
for this one (256 vs 4096 for the Perlin noise modules). This can make some nice
metallic or tone like noise sounds. I should add a button to the Perlins to invert
the new input. As it is now the new input is set by default, this is not always
I've added the invert option ( i(nvert) vs n(ormal), the latter being the default
value on the noise modules, the former for the tone module).
And another new module, Random scales … the help blurp says something like:
This module implements a scale randomizer. Each time the rnd input goes from
inactive to active, or when the rnd button is clicked, a new random scale mapping
will be computed. A scale will always have 12 notes per octave, and all octave
mappings will be the same (with an octave shift, of course). Within an octave the
12 notes will be randomly mapped to 12 (probably, but not guaranteed so, it's
random after all) different notes.
A simple arpeggiator
On each clock on the 'new in' input a new input sample is is taken and added to a
list of samples, the oldest value present will be dropped from the list then.
This list can be left unsorted, it can be randomized or be set to play the lowest
or highest note first .
The list length is set with the length control.
On each output clock on the 'new out' input the next stored value from the sorted
list will be output.
In random mode the order in the sorted list will be randomized when the playout
wraps back to the first value.
In unsorted mode the playout will be the recording order.
On the input side an acceptance filter can be applied. All incoming values can be
accepted, values differing from the previous value or values not present yet in
the list of samples.
The toggle input when inactive causes the selected sort order to be in effect and
when active the next sort order will be used. This can be used to toggle between
low to high and high to low modes, for instance.
When there are not enough input values available (yet) arbitrary values will be
clocked out until the playout counter wraps back to zero.
The reset input (or a global reset) will cause the playout pointer to be set back
to zero without changing any stored values.
And another new one, a probabilistic sequencer.
For each note the probability with which it will be played can be set with a
slider (and this value can be multiplied by the value on the associated input).
Notes have to be be enabled before they can sound, and note enables can be
selected from a scale preset.
The presets will be dynamically loaded from a file wren.scale that must be in the
same folder as the Wren executable file. When this file does not exist
Wren will create it. After that you can edit it with a text editor
(like Notepad for instance) and Wren will not touch it anymore.
A selected scale can be altered with the note buttons, and such a change will be
saved with the patch (making the shown scale preset name meaningless, of course).
The rnd button will set a random probability distribution, the clr button will set
a flat distribution. The distribution can be altered with the tilt control. A zero
value means that there is no tilt, a positive value makes higher notes more likely
to be selected and negative values will produce more low notes.
A transposition can be applied to the selected scale with the trans(pose) control.
C is the 'neutral' base note (not leading to any changes). Transpositions are not
reflected in the shown note pattern. The low and high note controls limit the
range of possible notes.
The sm(oo)th controls determine the likelihood that the next random value is
about the same as the current one. So with a larger smoothness the results will be
Added noise type selection to various noise modules (OSC and LFO). The default
type is Linear (which was the only available mode before), the added types are
Gaussian (with a fixed sigma of 1.0) and exponential (with a fixed lambda of 3.0).
This affects the Noise, NoiseTrig, NoiseLfo and NoiseLfoTrig modules, but
backwards compatibility was maintained.
Added mode control to the Pattern module. A mode can be set on each step, it can
be normal (nrm), random (rn1), weighted random (rn2, or rn3) or skip. Normal
meaning that it will do it's full count. The random modes will generate a random
number [0,Count] and use that as the step count. The first random mode considers
all numbers in the interval, the second random mode only divisions by 2, and
likewise rn3 uses divisions by 3. Skip will just skip the step. Also added
individual step outputs which will go active when the associated step causes an
output pulse to be made. The step outs will produce a 'per step' copy of the main
Added clear inputs to arpeggiator and poetry modules to allow them to forget
stuff. These are latching inputs capturing a low to high transition. When they are
in the set state a next value to be clocked in will not be the input value but
zero instead. After having been processed the set state will be cleared.
Added an Amplitude / Ring Modulator module, which is a multiplier with control
over modulation depth and modulation offset. This makes it a bit easier to apply
less than full depth AM or RM to a signal. The input signal type can be set, and
it can do a fade between amplitude modulation (AM) and ring modulation (RM).
And made a simple pattern rewrite module for which a couple of rewrite rules can
be specified, and an expansion level. There is a small alphabet of the letters A,
B, C, D and E. For each letter a substitution is specified in terms of other
letters from the same alphabet. For instance, given the rules:
Then a number of expansion steps is specified resulting in patterns being
generated from the start symbol 'A'. With the rules above the successive patterns
- A → ABC
- B → C
- C → D
- D → AC
- E → B
etc. The maximum depth to be set is 8, which would result in a pretty long pattern
already with the rules above.
- A → ABC
- ABC → ABCCDEDEACB
- ABCCDEDEACB → ABCCDEDEACBACBABCDEC
At each positive input step a next symbol from the generated pattern is selected
and the corresponding output will be made active. At the end of the pattern it
will start again from the beginning. Some rules (or all) can be left blank for
simpler patterns. All letters must be from the set [A..E], everything else will be
ignored for pattern generation.
This is after an idea found at
RobotPlanet, which in turn references this article.
Decided to generate all 8 expansions whenever the rules change, which made it
possible to have depth modulation – which I've added.
Made a variation on the previous module generating values instead of events. It
also has a couple more rules to compose with. It adds a lookup system so that for
each active step a value is put out. The value knobs are mode controlled, one of
the modes being 'note value'. There are the usual dB and linear ranges too.
A common chain input is available which is simply added to the current rule based
value, and then there are individual rule chain inputs which are added to the
output only when the corresponding rule is active – with this the module can
be used as a rule based multiplexer too (when all values are set to a neutral C4
or to zero, depending on the selected mode).
A TuneSmithy module. This is a melody generator after an idea by Robert
Inventor and it is explained here. The sequence can be arbitrary long in principle, but
decided to cap it at 1024 steps. The pattern is a comma separated list of integer
values. The second link above explains the inner workings.
in version 2016.8.21.0
When during live morphing new modules are inserted some odd stuff happens. Ok,
only when the module does odd stuff, see next item – the GVerb module would
crash. Ah, and modules get set to all zero values when inserted while live morph
is active. Aha optical mostly … the first variation gets set from the
default knobs and all other variations get set to all zeros, which looks confusing
in a live morph situation. Still it would be better that on insertion of a new
module all the variations would be be set the same – according to the
default knob positions. Ok, fixed that.
Live morphing when the GVerb module is present sounds bad (even when it is not
being morphed), for FreeVerb it is fine tho. Ah, it was being recreated all the
time even when the parameters did not change, and then it would crash. Ok, fixed
it. But there also is the issue that automation will change parameters that it
should not change. Ok, stopped that too.
Bug in DataGraph where the rightmost point would always end up top right (1,1)
even when it would not be drawn there. Fixed.
The active variation randomizer got mixed up a bit with the randomize function
from the morpher, unmixed that. The active variation randomizr is selected from
the action menu or by pressing 'R' on the keyboard and it sets random values for the
current variation only. The randomize function for the morpher sets random values
for variations 2 to 6 (for quickly generating a handful of new genes).
Bug in ScaleQuantizer, the selected scale selection is not properly read from a
saved patch, the buttons are OK though. Was an issue for all dynamic count
selectors and got introduced with the introduction of variations. Fixed now.
Oopsie .. the filter inversions used '-' for 'off' (which can not work anymore
after some changes on how dashes are handled for popup menus in relation to
automation) changed them to '.'.
in version 2016.8.20.0
Made a Time Of Day (Tod) module which is a saw tooth LFO with a period of 24 hours
synced to the local PC clock. So at 00:00 it's output value will be zero and at
01:00 it will be 1 / 24. The clock has millisecond resolution. The output value
may drift a bit as windows does time syncs when it feels a need – but it
will be the best estimate of the current time. A couple of level shifters and
ChebGen modules could be used to obtain signals that run faster. Like first make
the signal bipolar, then multiply by 24 (first by 12 then by 2 using two ChebGens
in saw mode) and then level shift it again to unipolar positive to get a signal
with a rate of one hour. Then the same trick with a factor of 60 to get minutes,
60 again for seconds.
Hmm … instead, I've just added a couple of outs for hour, minute and second.
Made a new option for the morpher, it can do a live morph over the breeder too
now. Normal morphing is between the left and the right morph and morphing over the
breeder uses all eight variations present in the breeder instead (when the breeder
is morphed with the Morph button this is equivalent to the non breeder morph, but
when mutate or mate is applied variations will be introduced). This new option
tends to (depending on settings and actions) give more lively morph results (like
for the XY controls the dot can then move in a rough curve instead of in a
straight line only).
And made a new 'soapy' worm shape – how cruel it now seems to hold them in a
cage like this …
I've turned the morpher code inside out a bit, that is, I've made variations for
patches and based the morpher on that. Variations are stored with the patch, so
they will still be there after patch reload. As the variation values are stored in
the controls (knobs and such) now, this also means that module additions and
deletions do not mess up the the the worms for other modules anymore. All this
needs some work though still; the worms are not always updated correctly, and
there is an issue with XY controls loosing data or something – but it
stopped crashing at least :-)
Changed the randomizer as well, it now works through the same mechanisms as used
by the morpher. It will set random variation values for the active variation now
(which then in turn moves the knobs, the randomizer used to work on the knobs
directly (which would then change the current variation)). It is all a little
easier this way. Anyway … some more work to do on this.
Most stuff is working now, but drag-drop of worms is messy still … some
more work …
But it's not working well; turning some more stuff inside out – the
mutations are all carried out on the patch now and then update the worms, instead
of working on the worms and updating the patch. Let's see what surprises will
arise from that …
Ok, that goes better, it seems to all work now as it should – except for it
being very slow all. Not sure if its the editor updates or the worm updates
… there are a lot of params that change on a live morph … more work
Improved the speed somewhat, still not very fast, but it will do I guess.
Livemorphs are controlled trough the lights update routines, that is not ideal
(as the tempo goes all over the place) and this should be changed. Ok, changed
that, it is currently updated at a rate of 10 Hz triggered from the audio
generation rate (and so independently of the lights update rate). So this should
work properly for recording to disk as well. The exact rate may change later from
10 Hz, not sure yet, or make it a user pref maybe.
Live morphing works over the variations now, and I've removed the left/right morph
worms. When a left/right morph is wanted you can do a morph operation on the
breeder, then copy the worms to the variations and then perform the live morph. So
with less options the same functionality is still available.
Added a couple of buttons to the randomizer / morpher screen to make copying
easier. Drag / drop now works properly as well. Moved the live morph options from
the randomizer to the main toolbar – turn auto mode on or off, and the morph
control knob. Morphing no longer changes any variations, instead there now is a
temporary variation which is being used.
Changed some keyboard shortcuts related to the randomizer / morpher and added some
(Ctrl+R still is recent patch reload).
- R - randomizes the patch (was Ctrl+Shift+R).
- Shift + R - toggles the exclusion visibility. (was Ctrl+Shift+Alt+R)
- Alt + R - shows or hides the randomizer window.
For changing variations you can use the keys 1 … 8, or they can be selected
by clicking on a worm in the toolbar or from the View menu. Variations can be
dragged from one spot to another, or even from or to the randomizer window.
Made it so that it is still possible to see all of the toolbar in the space needed
for four horizontal modules … which is like 1024 pixels. This would be a
practical minimum value for the horizontal screen resolution needed for
Wren (see image above). And also added the mutator commands in there
(as well as into the action menu).
Had to change the patch format again … not really for the variations, but
could not store the active variation with the patch in the current format. Made
the format a little more flexible again, so that future patch parameters will not
need a new patch format (which already was the case for control and module
parameters). Anyway, it's backwards compatible, but not forwards, as in: old
patches can still be read.
Made an Auto module which can perform Auto-randomize, -mute, -mate or -morph in
the same way the buttons in the randomizer / Mutator window do. Making this a
synth that can truly auto-mate!
The '-' avoidance code has a bug it seems … causing Wren to
hang in an endless loop on some patches when the randomizer is used –
investigating. Ok, solved that, but still saw dashes on morphing … fixed
Which … of course … introduced an issue for selectors having only
two values and no dashes at all, fixed that too.
module can not support randomization on the delay parameter. I disabled that. The
problem is that when delay and shift are changed at the same time invalid internal
values can occur. All automation has to be and was set disabled for that knob.
When a control was set to be non-randomizable, or non-automatable actually, and in
the patch it was stored to allow for randomization the red exclusion rectangle
would not show. Fixed that, and when such a patch is saved the control will be
saved as non randomizable too.
PitchShift module would produce denormals under some conditions. Probably fixed it
with normalizing the linear interpolation code's output.
Gabe made some new bitmaps for the looks. I've made some new ones too — had
a lag of about 40. Looks file got updated to 2016.8.2.
in version 2016.7.27.0
Fixed the patch randomizer for selectors having '-' values (these are meant to
generate separators in the associated popup menu). Trough the menu interface such
items can not be selected, but the randomizer found 'm allright …
Ah, and clicking on a selector or using the cursor keys or the space bar hits them
as well. Fixed that too.
Made the Pad, Spiral and DataGraph modules randomizable.
I'm working on a patch mutator, it's very much like what the G2 has. Still some
quirks to iron out on that, like what to do when the patch gets modules inserted
or deleted. The current implementation does not handle that as it should. Also the
images seem to not always be drawn correctly. Ok, found the issue, I'm misusing,
sort of, some selectors as indicators (on the ScaleQuantizer). This means that the
chord selector has to be disabled for randomization. It should maybe also indicate
that the key selection does not map to the selected chord anymore. But then again
… I could just consider the selector to be a preset selector only, not
reflecting the actual state. On a patch reload the actual keys will win anyway.
I may change this when i get ispiration.
I've made a FAQ entry for the morpher / randomizer.
The forum thread is here, it may have some info not listed here.
Made the mutator work for Pad, Spiral and DataGraph too. There are some issues
with the DataGraph, as points can be added to or removed from it. This means that
the number of data points present in the mutator may change. What I did for now is
that such a situation is detected and the mutator will be re-initialized (which
looses all the current worms in the mutator, making a random set of new ones, and
the scratch area will be cleared). Module insertions and deletions are handled in
the same way.
Added two extra worms to the mutator, a left and a right morph, and a knob to fade
between these two. Also added a modulation option to the knob, and a new module
which can do the fade from the patch. This works at the lights rate, which is user
controllable, but it can not be very fast nor can the exact timing be very
predictable, as a lot of screen updates need to be done. Still for slow morphs
between two variations it would be nice. It is possible to have more than one
LiveMorph module in the patch, but things may get a bit jumpy with that.
The randomization exclusion works for both the randomizer and the mutator in the
same way. There is a keyboard shortcut to visualize the exclusions, and also when
the randomuzer / mutator window is active exclusions will be made visible in the
patch (with red rectangles around the excluded controls or modules).
Made it so that when patch randomization is requested (as opposed to single
control or single module randomization) and there are no modules selected, that
all (randomizable) modules are randomized.
Changed some code for the components introducing a couple of interfaces for them:
IAutomatable (for MIDI control), IRandomizable (for plain randomization) and
ICollectable (for controls that can contribute to the genome used for patch
mutation). This makes things a bit easier to program, I hope … it was quite
some work. Please note that non automatable controls can not be randomized either.
In general anything that needs patch recompilation can not be automated or
in version 2016.7.23.0
Made a scale control for the Reverb module. It sets the internal length of the
delay lines to some factor of the original length. This alters the color and
buzziness of the reverb. As the lengths of the internal delays are modified a
change of scale needs patch recompilation( e.g. a change causes a brief silence).
Added an End Of Cycle (EOC) output for the AHD and ADSR envelopes. When fed back
into the trigger input turns the envelope into an LFO, but can it be used to chain
envelopes as well such that one triggers after another.
Moved the Constant, Amplifier and Ratio modules to the Math tab. This distributes
the modules a bit more evenly over the tabs.
Working on a patch randomizer. Randomization is possible on Knobs, Sliders and
Selectors. It is possible to randomize a single control, all controls on a module,
or al controls on a selected set of modules. There will be options to disalow
randomization on selected modules and on selected controls. The action menu will
get an option to make visible the modules excluded from randomization.
Made a randomizer control wimdow to make it possible to exclude module types and
control types, partly by category.
For the randomizer I had to change the patch format to allow for a new module
parameter type. Old Wren patches can still be read by the new
Wren but new Wren patches can not be read by old
Wren versions. I did make the change in such a way that in the future
it should be possible to add new module parameter types without altering the patch
version. This already was the case for new detail (knob etc.) parameters. Old
Wren's should then just skip the parameters they don't know about.
in version 2016.7.4.0
Made a popup menu for the DataGraph, or for it's DataMaker component rather. Some
wave shapes can be selected and some basic operations on the data can be selected.
With the symmetries there are some duplicates in the operations, like a Bell
shape is the same as a vertically flipped cosine, and for the squares there are
some duplicates as well. Added load from file and save to file to the menu. Added
a left — right adjustment feature as 'make loopable' to the context menu.
MixMS8to1 and MixM16to1 were not working without modulation signals being
connected, fixed that.
The timer controlling the lights and VU meter updates is started in running mode.
When the startup is slow for some reason this may cause the VU meters to be
updated from non–existing objects. Fixed that by disabling the timer at
startup, after each patch compile it was turned on already, so things should be
all fine once an actual patch is present.
Decided to make all timers inactive during startup to enable them only in
FormShow or even later — when needed. Also typed some extra checks around
the VU meter calculator objects to see if they were allocated before being used.
MIDI TX messages were logged from the audio thread directly (when logging was
enabled), which was a bug. Fixed that.
Error in DataGraph module. It was meant to react to double left clicks or
ctrl+left clicks by adding a new data point, but ctrl+double left click would add
two points and would then mess up the order of the points. Fixed that and checked
at other places if such a problem could exist elsewhere – did not find such
There is some debug stuff left in the looper module (like the light), this should
be removed once the thing gets settled … which currently it is not.
Delayed help file creation a bit so that the looks are completely set up before
the images are being created – image previews on the module selector look
Made the trigger LEDs for the envelope modules light up 125 ms always, even for
very short trigger pulses. Some more will follow as some modules output very short
trigger pulses that could not been seen on all input lights. This also means that
for a non changing input signal the light will go off after a while, it will only
show the trigger moment. made an error in this making the sample and hold turn
into a track and and hold … and fixed that again.
It may be the case that there is a denormals issue for the Formant2 module,
running some debug tracking on that, but lost focus … focusing again
… After 10 or 11 hours of runtime on a patch, yup, got a denormal report,
looking into the why now, it is on the output signal, should not be possible
inspecting the code, odd.
Restyled the module documentation a bit and added a link to it in the main menu of this page.
Also for newer modules I started to add links from the module images in this page
to the documentation page (meaning that module images here are clickable now).
Also fixed some inaccurate help text.
I've started using a mark–down processor for easier markup of the generated
help file. See the Acknowledgements section for
more on this. This will allow for clickable links in the help, better looking
lists, etc., Expect more help restyling.
Changed some things for popup menus. They should now popup near where the cursor
is instead of near where the top–left of the control happens to be. Also in
the patch editor I've made the menu key work for the element the mouse cursor is
Moved wire toggling and wiggling from the edit to the action menu, keeping the
same shortcuts (Ctrl+space bar and Ctrl+W)
Made three new mixer types MixQS2to1, MixQS1to1 and QuadPan (which actually is a
panner, but it's on the mix tab …). Although these do have blue connectors
they are intended to be used for audio mainly and when audio signals get connected
the connectors will change to the audio rate color. The panner uses an equal power
distribution only. The mixers allow for 24 dB of amplification.
Made an audio to control rate converter, which can be used to keep large areas of
a patch from becoming red.
Added a 'retrig'(ger) option to the LfoTrig module. When set into retriggerable
mode and when the trigger input goes inactive and active again during the current
pulse train the module will be reset to start the train anew. The default setting
is 'normal' for compatibility with older patches. Together with the DataGraph
module this could be used to make retriggerable arbitrary envelopes, for instance.
Hmm … not quite … anyways …it seems useful … maybe.
Added a Polar
module, it translates rectangular coordinates into polar coordinates.
Added a Rectangular
module, it translates polar coordinates into rectangular
Made a stereo version of the looper. It still has the drawbacks of the mono one,
but really wanted stereo.
Added a Spiral module, an experiment really. Per spiral winding of mouse movement
a settable amount of note steps is added. Along the positive X axis the white
places correspond with the steps. As this internally works with polar coordinates
I made outputs for the angle (phi) and distance / radius (norm) as well. The len
represents the spiral length for the current (X,Y) location (from which the note
output is calculated). So at least it doubles as a Polar sort of Pad module. (But
the latter can also be done by adding a Polar module after a Pad.)
Added an unattenuated frequency control input for the Lfo, SquareLfo and RandSig
modules. This makes it easier to add overall speed control to a patch.
Added an MConst module for selecting some more or less often used mathematical
constants, like 1, 2, e and 𝜋 etc.
Added a 'wrap' mode to the DataGraph module, the standard behaviour was 'clip',
which still is the default. In clipped mode an out of range input value will clip
on one of the graph edges and in wrapped mode it will wrap around and come in on
the other side again (modulo operation).
Added f(x)=x·𝜋, f(x)=x·2·𝜋,
f(x)=x∕𝜋 and f(x)=x∕(2·𝜋) functions to the
Monadic function module. Also added f(x)=floor(x), f(x)=round(x), f(x)=ceil(x) and
The Pad and Spiral module did not set their output values after a module load or
patch change, it needed a movement first – I've changed that. I may have
thought this to be a feature for the Pad module, but for the Spiral it was just a
Removed all the all-too-obvious email addresses from the web page and
Removed some unused stuff here and there from the code, making the executable a
Added some volume damping around patch recompile operations, the worst of the
recompilation click is out now.
I've made an option to disable automatic doc file generation. This option is off
by default (so docs will be generated out of the box), and this feature will only
work when you use the old wren.ini file, e.g. when you copy the new executable
over the old one (or copy the old ini file to the new location). You can always
manually generate documentation from the Settings Screen [F3] by using the
'generate documentation ...' button there. Note however that when no docs were
generated the popups from the module selector will not show a module, or an old
version of the image.
I've added command line passing of a patch file name. You can now associate
Wren with '.wren' patches in windows such that double clicking on a
patch will open it in the Wren instance that got associated. It is
still possible to run multiple Wren instances, but they will have to
run from different directories now, and patches opened through the explorer will
always open in the associated instance. When starting Wren directly it
will still open the last patch it had loaded as well. BTW it is possible (it has
always been) to copy patches, or parts of it, from one Wren instance
to paste them into another) or into a text editor, or whatever program that will
in version 2016.6.5.0
Changes in text controls and data graphs marked the patch for needing
recompilation which was overkill. It should have been marked for change only.
Changed that, and internally renamed some 'PatchChanged' stuff into 'Recompile'.
While all modules seem to be properly execution locked now during heap operations
the patch as a whole was not locked. Changed that.
MIDI CC assignments to knobs are not working properly – CCs move the knobs
alright but the synth value is not changed. Ok fixed that, but now on very fast
MIDI I'm getting all kinds of memory issues. Ok, that actually is due to some
errors in MIDI transmission – it was doing memory allocations from the
audio thread. Ok, four bugs fixed in this … messy, but fixed now.
Added exponential FM control to looper. Oh that it was no longer clicky was a
mistaken observation, with long loop times or record being off it is not too
noticeable maybe. And a remark about the interpolation mode, all pass mode is not
to suitable when the interpolation point moves relatively fast, that is for
in version 2016.5.29.0
Older release notes