Colour Seperator (.swf and source)
Update May 27, 2008: Hey guys I just found a much better way of doing colour separation. The code below takes a very brute force approach. It seems the Flash engineers were one step ahead of me though. There’s a method called copyChannel() which essentially takes a selected colour channel from one bitmap and moves it into another. The below code is still a decent introduction to parsing through bitmaps and bitwise operators. It’s just not the efficient way to do this task.
After the Red tick failure this morning, I wanted to get right back into it and do something quick.
In this project I:
A) Load in an external image
B) Read in all of the image’s pixel values and split the data in to red, green, blue.
C) Feed the colour data into seperate layers
D) Animate ’em!
I’ll go into the code after the break.
But first:
I stumbled upon this link while looking into bitwise operators:
It’s a great resource and I’d strongly suggest looking into it, especially if you’re not familiar with getting colour data out of hex numbers.
Hold the mouse button down to automatically align the layers
Click here to see the full size version
NOW ON TO THE CODE!
First I create an object for each layer. Each layer is a just a bitmap + bitmapData and some position data.
var angleSegment:Number = Math.PI * 2 / 3; blue = new colourLayer(imageWidth, imageHeight, 0); green = new colourLayer(imageWidth, imageHeight, angleSegment*1); red = new colourLayer(imageWidth, imageHeight, angleSegment * 2);
This hung me up for a while; how do I recombine the colours once I have them seperated? I tried changing the alpha value for each pixel to 0.33, which looked really muddy. Then I tried some other stuff which was just shooting in the dark. Finally, I stumbled upon the idea of using blend modes and found that 'Difference' did the trick... the problem is I don't know why it works! Maybe someone who understands colour theory could explain it in the comments.
green.blendMode = BlendMode.DIFFERENCE red.blendMode = BlendMode.DIFFERENCE
Next is a for loop which goes through every pixel in the source Image and rips out its red, green and blue values. Then I assign those single colour values to the red, green or blue layers. This is where the bitwise operators come in handy. Here's that link again in case you didn't click it the first time.
for (i = 0; i < imageHeight; i++) { for (ii = 0; ii < imageWidth; ii++) { var setColour:Number = bitmapAlias.getPixel(ii, i); var redVal:Number = setColour >>> 16 & 0xFF ; var greenVal:Number = setColour >>> 8 & 0xFF; var blueVal:Number = setColour & 0xFF; redVal = redVal << 16 | fillerVal << 8 | fillerVal; greenVal = fillerVal << 16 | greenVal << 8 | fillerVal; blueVal = fillerVal << 16 | fillerVal << 8 | blueVal; red.assignPixel(ii, i, redVal); green.assignPixel(ii, i, greenVal); blue.assignPixel(ii, i, blueVal); } }
Really, those are the only tricky, bits. If there are questions drop them in the comments!