AS3/Flash10 software synthesizer SiON goes to version 0.6

SiON goes to version 0.60

Now, the ActionScript software synthesizer “SiON” is updated to version 0.6. You can get the newest version from following link.

SiON Development Center in spark project
SiON version 0.60 ASDoc

In the SiON version 0.6, the interfaces are basically same as previous, but it suggests one new feature “SoundObject”. Here’s the example on wonderfl.

SiON SoundObject Quartet

The Arpeggiator, BassSequencer, ChordPad and DrumMachine are the inheritances of SiON SoundObject. The SoundObject brings an feeling of ‘DisplayObject’ to the operations of SiON’s synthesizer.

Let us explore a tidbit of sample’s source code. The concept of SiON SoundObject consists of 4 modules, the SiONDriver, SoundObjects, Synthesizers and Effectors (shown in line 16~54).

The SiONDriver is the centeral processing unit of all SiON’s sound, you have to create one new SiONDriver and call play() method. And you might access some SiONDriver’s properties and methods to set up general settings (BPM, effector and so on) (shown in line 76~83).
driver = new SiONDriver(); (line 65)
...
driver.autoStop = true; // set auto stop after fade out
driver.bpm = 132; // BPM = 132
driver.effector.slot0 = [equaliser]; // The equaliser is applied to slot0 (master effector)
driver.effector.slot1 = [delay]; // The delay effector is applied to slot1 (global effector)
driver.effector.slot2 = [chorus]; // The chorus effector is applied to slot2 (global effector)
driver.addEventListener(SiONTrackEvent.BEAT, _onBeat); // handler for each beat
driver.addEventListener(SiONEvent.STREAM_START, _onStartStream); // handler when streaming starts
driver.addEventListener(SiONEvent.STREAM_STOP, _onStopStream); // handler when streaming stopped
...
driver.play(null, false); (line 193)

The SoundObjects provides a sequence controler. You can control the sounding patterns in real time by properties (following code is from Arpeggiator’s setting line 91~101). In this exapmle, you can feel the SoundObject’s sound controling especially in the Arpeggiator’s large square pad. All SoundObject classes belong to org.si.sound package.
Ar = new Arpeggiator();
Ar.scaleName = "o6Emp"; // scaled in E minor pentatonic on octave 6
Ar.pattern = [0,1,2,3,4,2,3,1]; // basic pattern is "egababg" in MML
Ar.noteLength = 1; // note langth = 16th
Ar.gateTime = 0.2; // gate time = 0.2
Ar.effectors = [autopan]; // apply auto-panning effector to Arpeggiator (local effector)
Ar.volume = 0.3; // dry volume = 0.3
Ar.effectSend1 = Ar.volume * 0.4; // effect send for slot1 = 0.3 * 0.4 = 0.12
Ar.effectSend2 = Ar.volume * 0.5; // effect send for slot2 = 0.3 * 0.4 = 0.15
...
Ar.play(); (line 198)

The Synthesizers provides a voice controler. This class simplifys the SiONVoice’s settings, and supports a real-time voice charactor chagings on a SoundObject. In this example, some components are connected to the synthesizer’s properties (especially in BassSequencer’s envelop controls) and you may feel the voice character changing on it. (following code is from Arpeggiator’s WaveTableSynth line 106~109). All synthesizer classes belong to org.si.sound.synthesizers package.
waveTableSynth = new WaveTableSynth();
waveTableSynth.color = 0x1203acff; // wavecolor value
waveTableSynth.releaseTime = 0.2; // release time
Ar.synthesizer = waveTableSynth; // apply synthesizer

The Effectors represents the sound effector units. You can apply effectors to the SoundObject like filters to the DisplayObject (please refer above code).
One remarkable point on effectors is that there are 3 types of connections, master, global and local effector. The master effector preocesses the final output of all SiON’s sound, the global effector preocesses the effect send pipe and the local effector processes only one SoundObject’s output. The arrow diagram of effector connection is as shown in below figure. All effector classes belong to org.si.sion.effector package.

SiON SoundObject's Effector connection arrow diagram

SiON SoundObject's Effector connection arrow diagram

The SiON’s SoundObject brings the simple interactive synthesizers to your flash contents. Enjoy it !

Decrement versus Increment in Loop

Adobe’s “Optimizing Performance for the Flash Platform” recommends that “Use reverse order for while loops” in its “Miscellaneous optimizations” section.

while (--i > -1)

But according to my test significant difference could not be found between decrement and increment. In other language they said that decrement and increment are identical.

The pre-increment/decrement is a little faster than post, which is included in my test, though.

Quaternion notation of Vector3D

The [Help] of the Vecror3D.w property mentions about the quaternion notation as follows:

Quaternion notation employs an angle as the fourth element in its calculation of three-dimensional rotation. The w property can be used to define the angle of rotation about the Vector3D object.

But this sounds like explanation of the axis angle (see Orientation3D .AXIS_ANGLE Constant). The axis angle uses a combination of an axis and an angle to determine the rotation. For an argument of the Matrix3D.decompose() or Matrix3D.recompose() method Orientation3D.AXIS_ANGLE can be specified as the orientation style used for the matrix transformation.

Try to rotate a Matrix3D object 180 degrees (π) around the axis (1/√2, 1/√2, 0).

The axis of rotation

var myMatrix3D:Matrix3D = new Matrix3D();
var axis:Vector3D = new Vector3D(Math.SQRT1_2, Math.SQRT1_2,0);
myMatrix3D.prependRotation(180, axis);
var axisAngle:Vector3D = myMatrix3D.decompose(Orientation3D.AXIS_ANGLE)[1];
trace(axisAngle, axisAngle.w);

The frame action above outputs as follows:

Vector3D(0.7071067094802856, 0.7071068286895752, -2.339619844353034e-24) 3.1415927410125732

[Note]: 0.707… = 1/√2 and 3.14… = π radians = 180 degrees.

The (x, y, z) coordinates represents the axis and Vector3D.w property is an angle of the rotation. This result seems to fit the explanation of the [Help] quoted above.

But the quaternion notation determine the rotation by the four value. The following expression of the quaternion Q represents the rotation of θ around the vector U.

U = (x, y, z) and |U| = 1
Q = (cos(θ/2); sin(θ/2)U)

Then try to rotate a Matrix3D object 60 degrees around the y axis (0, 1, 0).

var myMatrix3D:Matrix3D = new Matrix3D();
myMatrix3D.prependRotation(60, Vector3D.Y_AXIS);
var quaternion:Vector3D = myMatrix3D.decompose(Orientation3D.QUATERNION)[1];
trace(quaternion.w, quaternion);

The frame action above outputs as follows:

0.8660253882408142 Vector3D(0, 0.4999999701976776, 0)

These numbers represent the quaternion of 60 degrees’ rotation.

0.866… = cos(60/2) = cos(30)
(0, 0.5, 0) = sin(60/2) (0, 1, 0)