Category: Source Codes

source code

  • Organic Turing Pattern

    Organic Turing Pattern

    In this post i will present an experiment which i did a few months earlier, but because lately i was pretty occupied with various job related activities and with setting up this new blog (transferring the old content to the new host – plus a lot of other stuff), i have no time to publish this new experiment. More about below, but until then a few words about the background, inspiration and some of the key challenge i have faced during this process.

    This is an experiment inspired by a thoroughly explained article about the concept behind what is generally known as Turing Pattern. The Turing Patterns has become a key attraction in fact thanks to Jonathan McCabe popular paper Cyclic Symmetric Mutli-Scale Turing Patterns in which he explains the process behind the image generation algorithm like that one below, about what Frederik Vanhoutte know as W:blut wrote on his post:

    Quote leftIf you’ve seen any real­ity zoo/wild-life pro­gram you’ll rec­og­nize this. Five min­utes into the show you’re con­fronted with a wounded, mag­nif­i­cent ani­mal, held in cap­tiv­ity so its care­tak­ers can nur­ture and feed it. And inevitably, after three com­mer­cial breaks, they release it, teary-eyed, back into the wild. It’s a piv­otal moment that turns their leop­ard into anyone’s/no one’s leop­ard.Quote right

    That’s the feeling which emanates when you first see the organic like, somehow obscure (some may go even further and say: macabre or creepy) thing which is known as a Turing pattern. At first moment when you are confronted with it, some kind of emotion (be that fear or amazement or just a sight) is resurfaced. Definitely won’t let you neutral.

    This is the emotion which pushed me to try to implement it in Actionscript. (In parentheses be said this is not the best platform for computation intensive experiments.) Felix Woitzel did an amazing remake adaptation of the original pattern in WebGL. The performance with a good GPU is quite impressive. Maybe in the future i will try to port in WebGL. Anyway, there is another nice article by Jason Rampe, where he explains the algorithm of the Turing Pattern.

    So let’s face directly and dissect the core components of the algorithm.

    The basic concept

    The process is based on a series of different “turing” scales. Each scale has different values for activator, inhibitor, radius, amount and levels. We use a two dimensional grid which will be the basic container for activator, inhibitor and variations, all of them going to be of typed arrays (in our case Vectors.<>). At the first phase we will initialize the grid with random points between -1 and 1. In the next step we have to determine the shape of the pattern. For this case w’ll use a formula defined by the following method:

    for (var i:int = 0; i < levels; i++)
    {
    	var radius:int = int(Math.pow(base, i));
    	_radii[i] = radius;
    	_stepSizes[i] = Math.log(radius) * stepScale + stepOffset;
    }

    During each step of simulation we have to execute the following methods:

    1. Populate the grid with pixels at random locations. I’m gonna use a linked list to store the pixels properties: positions and colors. We will loop through all the pixels, the number of pixels will be defined by the grid with x height dimension.
    2. Average each grid cell location over a circular radius specified by activator, then store the results in the activator array, multiplied by the weight.
    3. Average each grid cell location over a circular radius specified by inhibitor, then store the results in the activator array, multiplied by the weight.
    4. In the next step we need to calculate the absolute difference between the activator and inhibitor using the the following formula: variations = variations + abs(activator[x,y] - inhibitor[x,y])

    Once we have all the activator, inhibitor and variations values calculated for each grid cells we proceed with updating the grids as follows:

    1. Find which grid cell has the lowest variation value
    2. Once we found the lowest variation value we update the grid by the following formula:
    for (var l:Number = 0; l < levels - 1; l++)
    {
    	var radius:int = int(_radii[l]);
    	fastBlur(activator, inhibitor, _blurBuffer, WIDTH, HEIGHT, radius);
    
    	//calculates the absolute difference between activator and inhibitor
    
    	for (var i:int = 0; i < n; i++)
    	{
    		_variations[i] = activator[i] - inhibitor[i];
    		if (_variations[i] < 0)
    		{
    			_variations[i] = -_variations[i];
    		}
    	}
    
    	//if first level then set some initial values for bestLevel and bestVariation 
    	if (l == 0)
    	{
    		for (i = 0; i < n; i++)
    		{
    			_bestVariation[i] = _variations[i];
    			_bestLevel[i] = l;
    			_directions[i] = activator[i] > inhibitor[i];
    		}
    		activator = _diffRight;
    		inhibitor = _diffLeft;
    	}
    	else
    	{
    		for (i = 0; i < n; i++)
    		{
    			if (_variations[i] < _bestVariation[i])
    			{
    				_bestVariation[i] = _variations[i];
    				_bestLevel[i] = l;
    				_directions[i] = activator[i] > inhibitor[i];
    
    			}
    		}
    		var swap:Vector. = activator;
    		activator = inhibitor;
    		inhibitor = swap;
    	}
    }

    As a last step we should average the gap between the levels by performing a blur technique for a nicer transition. We blur the image sequentially in two steps: first we blur the image vertically then horizontally.

    The challenge

    The most challenging part was related to the unknown factor about how well gonna handle the AVM2 the intensive CPU calculation. Well as you may have guessed not too well, especially with very large bitmap dimension and a lot of pixels needed to be manipulated, plus the extra performance loss “gained” after the bluring operation.

    For some kind of compensation benefits (in terms of performance) i decided to populate the BitmapData with a chained loop using single linked list, plus typed arrays as generally known the Vector.<> arrays are much faster compared to the traditional array stacks. After a not too impressive performance, i wondered how can i even more optimize the code for a better overcome. I decided to give it a try to Alchemy, and Joa Ebert’s TDSI, a Java based Actionscript compiler, as by that time was commonly known a better choice over AVM. Unfortunately i didn’t get too many support and helpful articles about the implementation and as a consequence my attempt was a failure, which resulted in a quite buggy and ugly output. After too many attempts without the wishful result, i gave up.

    That’s all in big steps. You can grab the source code from here. Feel free to post your remarks.

    ps: Be prepared this experiment will burn your CPU. 🙂

  • Sound visualization

    Sound visualization

    Sound visualization is one thing which I was always fascinated by. I stumbled upon this small Javascript experiment and thought would be nice to reproduce it in Actionscript, adding some spicy extra addons like interaction and sounds reacting shapes. So I decided to implement in Actionscript. Actually it went very well, in fact i only retained the core algorithm. The core algorithm consist in just a few lines:

    private function createSurface(a:Number, z:Number):Point3D
    {
    	var r:Number = W/10;
    	var R:Number = W/3;
    	var b:Number = -10*Math.cos(a*5 + T);
    
    	return new Point3D(W/2 + (R*Math.cos(a) + r*Math.sin(z+2*T))/z + Math.cos(a)*b,
    							   H/2 + (R*Math.sin(a))/z + Math.sin(a)*b, Z);
    }
    
    private function drawQuad(a:Number, da:Number, z:Number, dz:Number):void
    {
    	var v:Array = [createSurface(a,z),
    				   createSurface(a+da,z),
    				   createSurface(a+da, z+dz),
    				   createSurface(a, z+dz)];
    
    	_points = new Vector.();
    	_stroke = new GraphicsStroke();
    	_stroke.thickness = 1;
    	_stroke.fill = new GraphicsSolidFill(0x102020,0.95);
    
    	_path = new GraphicsPath(new Vector.(), new Vector.());
    	_path.moveTo(Point3D(v[0]).x, Point3D(v[0]).y);
    
    	for (var i:Number = 0; i < v.length; i++)
    	{
    		_path.lineTo(Point3D(v[i]).x, Point3D(v[i]).y);
    	}
    	_background = new GraphicsSolidFill(0x663399, 0.95);
    }

    First we create some quads using sine and cosine, multiplying by the radius, which is given as a constant. Then we store these quads on an array, setting their positions by calling the GraphicsPath.lineTo method. These positions are updated each time we loop through on an EnterFrame event listener. The fancy things happens here, where we use a fog variable to apply the shading effect by tweaking some depth illusion.

    And this is how it looks after implementation. By the way this is a good example of how robust and fast are <IGraphicsData> and drawGraphicsData functions combined.

    (Move the mouse to change the color shading intensity)

    After implementing the basic structure I thought – following the suggestion of some of the active members of wonderfl community – it would be nice to add some extra feature like sound visualization. Initially this little effect consists of some sinusoidally  curvy movement modifying the color intensity by the mouse position. You can check the effect by clicking on the image above.

    I was pleasantly surprised by the smoothly frame rate of the effect, so as i mentioned earlier the next step was to implement the algorithm for sound visualization. Thanks to makc3d audio API it was an easy job to obtain some samples which later could be used for the funky disco effect following the rhythm of the sound. This simple API connects to BeatPort portal, and by providing an unique key we can select from a various music genres. I opted for dubstep only because the high variation of beats can produce a very differentiated transition (a next step could be to implement an interface for selecting the different music channel).

    This is another variation.

    Playing with the values we can obtain different visualization effects. For example scaling up the bass bit rate we can obtain a nice upscaled flowing ring or reducing the radius value we should obtain a perfect circular cube like in the example below.

    Definitely a GUI interface would have been a better choice for playing with values, but because i put together this experiment in almost two hours i didn’t take the effort to polish the code. Maybe in a future time.

    (Scroll the mouse to jump to the next track)

    You can grab the source code here!