Dark Bit Factory & Gravity
GENERAL => Projects => Topic started by: mind on January 03, 2007
-
This time i've been experimenting some with something simliar to a cellular automata.
did some experimenting with some cellular automata the other day when suddenly i remembered this cool ripple effect some guy had written which was pretty similar to the CA i was writing, so instead of my normal CA algorithm i decided to use a modification of his algorithm and ended up with what you se below.
what you see in the screenshot are 3 buffers. first one is a photo of my girlfriend loaded into the program, the second is buffer2, where the data the automata use for the initial seed is stored(initially the same data as in buffer 1) and the third buffer holds the final result after 30 iterations with multiplier(sharpness basically) set to max.
cool thing about this automata is that its infinite, it just keeps going on forever and at later stages after some 2000 iterations it starts to resemble something similar to the bumps on sand dunes in the deserts.
anyways, application with full source will follow once i wind up at version 1.0.. as always, all feedback is appreciated.
-
Not sure what cellular automata means but it looks cool :)
-
Looks great Mind :) As Taj said before I'll echo. I can't believe how quick you can code these tools!!
-
I like the picture on the left the best ;) But the others are nice effects.
-
Mind,
can you stop coding for 20 seconds and do us a quick tutorial on how these effects are achieved? I can see that the one on the right is a differential of the one in the middle but I'm sure we'd all appreciate some paragraphs on how exactly you do these effects.
Its worth karma... :-)
As an idea, you should team up with a hardcore 3d programmer and write some code that does this in two processes:
Process 1
1. Renders any 3d in backbuffer
2. Captures the scene to an image, gives it to process 1
3. Checks for an available image from process 2 and draws it as a texture on a single quad in front buffer, filling entire screen
4. Renders music
5. loops
Process 2
1.Takes a new available image from process 1 and performs image manipulation(eg cellular automata if its fast enough) on it
2. Gives image to process 1.
3. Loops
Run it on dual core processor
-
mike(and others who are interested aswell :)) : http://en.wikipedia.org/wiki/Cellular_automata
shockie and taj: well, i've been doing some hobbie coding(in pascal :P) for several years so i have LOADS of stuff laying around, for example my fully functional texture generator.. now, since i recently started dabbling with delphi which gives me access to virtually unlimited amounts of memory and a nice RAD i can have a tool like this up and running in a matter of hours.. except for the texgen since that damn interface with the million sliders and calls for buttons etc took ages to code and was oh so boring... and no, it isn't differential in the abs(buffer2-buffer1) sense.. try it out in photoshop and you will see the difference :)
wham: yeah i like that picture alot aswell, its a wonderful face to wake up next to in the morning.. provided i wake up first, she has horrible mood swings in the morning lol.. (better hope she dosnt catch me writing this.. haha)
ok, so i'll explain how it's done(i figured it wasnt neccessery at first, since i will be releasing the code, but since my code can be pretty rough to understand, here we go :))
basically, what it is is a simple water effect, you know the boring blurred ones where you see virtual drops creating wave interference on whatever background you choose. explained here: http://freespace.virgin.net/hugo.elias/graphics/x_water.htm
im too lazy to write up an explanation on Cellular Automation, check the link up there :)
but ok, so we have a grid of cells(in this case a 256x256 texture with pixels) in 2 buffers. the third buffer in my program = image1 = for show, to let us see what we are working with. that one is never modified.
so, let's see here, we have 2 buffers.. for each frame we modify them both, finally we add or subtract them together and wack em into buffer2(which we then render to screen), rinse and repeat..
here's the procedure my innerloop is using to render the 2 images:
Procedure ripples(multiplier:byte);
var x,y:word;
temp:single;
begin
for x:=0 to 255 do
for y:=0 to 255 do
begin
temp:=(buff1^[byte(x)+byte(y)shl 8] +
(((buff2^[byte(x+0)+byte(y-1)shl 8] +
buff2^[byte(x-1)+byte(y+0)shl 8] +
buff2^[byte(x+1)+byte(y+0)shl 8] +
buff2^[byte(x+0)+byte(y+1)shl 8]) /4)-
buff2^[byte(x+0)+byte(y+0)shl 8]) /2)*(multiplier/256);
if temp > 127 then temp := 127;
if temp < -127 then temp := -127;
buff1^[x+y shl 8]:=round(temp);
temp:=buff1^[x+y shl 8]+buff2^[x+y shl 8];
if temp > 127 then temp := 127;
if temp < -127 then temp := -127;
buff2^[x+y shl 8]:= round(temp);
end;
end;
as you can see, we start by adding upp the center pixel of buffer1 with the top/left/right/bottom pixels of buffer2 and divide that by 4(basically what we have here is a standard blur, only exception is that we use data from 2 buffers). we then subtract the center pixel from buffer 2 and divide that result by 2 and finally we multiply it by a value ranging from around 0.80 to something closer to 2.0 or so. the reason why i use a division up there is to give it a range much easier to work with in the interface(0-255, even though i floor it at around 210 since anything below gives shitty results, ie a greyed out image).
then we do some range checking to make sure shit isnt over and/or underflowing and then we pop the result into buffer1. and finally we add the result of buffer1 and buffer2 together, perform some range checking here aswell and pop it into buffer2 which we then render to screen. even though i render both buffer1 and buffer2 the data in buffer2 is the final result, i just decided to re3nder buffer1 aswell only since it look cool when rendering..
now, the reason i use the temp float up there is because when i wrote this(modified more likely, sadly i dont remember who wrote the original so i cant give credit :() i was working in 16bits turbo pascal and didnt have access to large arrays of integers(256x256 for example) since real mode wont let me allocate chunks of memory larger than 65535 bytes, and thus i had to find a way to work around that, so i used an array of shorts instead and performed all my adds/subs/rangechecking in a single float variable(gg i made a pun, i win at wordgames :)) and then wacked the final result into the buffers.
i hope that cleared most of it up, im not very good at writing tutorials and whatnot, especially not coding tutorials since im not 100% set in the lingo department, i mean come on, after all i AM a 2d artist lol.. anyways, if you need some further explanation just let me know.. and also, if you want some information on how i generate some of my textures in my texgen feel free to ask me in the DEMTEX thread.. or check out the quick tutorial i whipped up by request, after winning a texgen competition over at cgempire.com.. http://www.cgempire.com/forum/tutorials-101/tutorial-procedural-texture-generation-basics-1121.html
finally, thanks for your feedback, and for "completion" i'll give you an exe to play around with.. keep in mind that it isnt finished so it lack certain functionality, like saving bitmaps, the neat zoom i have in my texgen etc.. but i'll get it in there eventually.. :)
-
I am astounded what can be produced by this from random input data with iterations around 1000. Then by playing with values of multiplier too. Quite a learning experience. Code look short, storage is almost nothing (for random input).
You are the master of texture Mind.
Karma++
-
This place is such a learning experience for me. It's nice to be able to come on here and learn something new most days. Thank you Mind ++ K
-
I am astounded what can be produced by this from random input data with iterations around 1000. Then by playing with values of multiplier too. Quite a learning experience. Code look short, storage is almost nothing (for random input).
You are the master of texture Mind.
Karma++
thank you taj :)
and yeah, with random values you can save the data in 4 bytes(1 int), 1 byte for seed(255 different seeds should be enough really), 1 byte for iterations(just have 0-255, and then multiply it by 10 or so in the generator), 1 byte for brightness and 1 byte for sharpness..
and the code to generate it is small, and as you can se in the app, pretty fast for realtime use too, even though i multiply/divide in places i dont need to etc.. could most likely make it work with left/right shifts instead..
-
and thanks to you aswell shockie :)
Edit: updated the zip file, attatching it to this post.. it now has loading/saving of generation parameters.. i did save random seed at first, but then for some retarded reason i decided to remove it, atm im just too lazy to add it, and my gf wants her computer back lol.. i'll update it later..
-
Fantastic work mind, and finally I started coding my own texture generation, thank you for work and inspiration :inspired:
So far I have coded:
-Sineplasma
-Envmap
-XOR texture
-CheckBoard texture
Ok, not much :P, but I've started yesterday...
TODO:
-Subplasma thing
-Distortion effects
-Filters...
When I got something usable I'll create a new thread at "Projects/Work In Progress"
:cheers:
[edited] Oh Karma++ :)
-
Very cool indeed.
-
looking good there rbraz.. if there's anything you need to know, feel free to ask.. :)
-
Fantastic work mind, and finally I started coding my own texture generation, thank you for work and inspiration
Out of interest, what size are you aiming at fior the final result? 4k or 64k or bigger?
Curious for obvious reasons :-)
Taj
-
Fantastic work mind, and finally I started coding my own texture generation, thank you for work and inspiration
Out of interest, what size are you aiming at fior the final result? 4k or 64k or bigger?
Curious for obvious reasons :-)
Taj
looks and sounds like 64k to me.. considering the amount of stuff he has, and the amount of stuff he's planning to implement.. a lil too heavy for 4k.. :)
-
Fantastic work mind, and finally I started coding my own texture generation, thank you for work and inspiration
Out of interest, what size are you aiming at fior the final result? 4k or 64k or bigger?
Curious for obvious reasons :-)
Taj
looks and sounds like 64k to me.. considering the amount of stuff he has, and the amount of stuff he's planning to implement.. a lil too heavy for 4k.. :)
@taj: Yes, mind is right, this will be more useful for intros less than 64kb, I'm also planning something for 4k ;)
looking good there rbraz.. if there's anything you need to know, feel free to ask.. :)
thanks dude for your support
-
How many really nice effects made by mind is there on this forum?? :D
Another great one!
-
How many really nice effects made by mind is there on this forum?? :D
Another great one!
i have a lot of free time :P and plenty of cool ideas aswell.