// Genesaver: copyright 2003 Sam Stafford. #include <math.h> #include <GL/glut.h> #include "globals.h" #include "DNA.h" #include "Brain.h" #include "Thing.h" #include "Animal.h" Animal::Animal( DNA* d ) :brain( d, muscles ) { prev = NULL; next = NULL; tagged = false; pchewing = A_C; achewing = A_C; fighting = A_C; mating = A_C; for ( int m = 0 ; m < 4 ; m++ ) muscles[m] = 0.0; energy = A_E; dna = d; short i; short rd = 0; short gr = 0; short bl = 0; char cs[10]; for ( i = 0 ; i < 4 ; i++ ) cs[i] = dna->hchr.colr[i]; for ( i = 4 ; i < 10 ; i++ ) cs[i] = dna->ichr[i - 4].colr; for ( i = 0 ; i < 10 ; i++ ) { switch( abs( cs[i] % 3 ) ) { case 0: rd++; break; case 1: gr++; break; case 2: bl++; break; } } i = rd; color = Red; if ( gr > i || ( gr == i && RandFloat() < 0.5 ) ) { color = Green; i = gr; } if ( bl > i || ( bl == i && RandFloat() < 0.5 ) ) { color = Blue; } // Diet is a weighted sum of 10 genes, with those in the // H-chromosome being most significant. diet = 0.5; float fd = 0.0; for ( i = 0 ; i < 4 ; i++ ) fd += float( dna->hchr.diet[i] * 0.9 * pow( 10, -i ) / 255.0 ); for ( i = 4 ; i < 9 ; i++ ) fd += float( dna->ichr[i - 4].diet * 0.9 * pow( 10, -i ) / 255.0 ); fd += float( dna->ichr[9 - 4].diet * pow( 10, -i ) / 255.0 ); fd *= 1.01; //correct for floating-point errors, lean toward extremities diet += fd; if ( diet > 1 ) diet = 1; if ( diet < 0 ) diet = 0; brain.input[9].axon = diet; //tell the brain what it eats } Animal::~Animal(void) { delete dna; } void Animal::Render() { glBegin( GL_POLYGON ); //Now the head. SetColor( color ); glVertex2f( x + A_R * cos( angle + 1.0 ), y + A_R * sin( angle + 1.0 ) ); glVertex2f( x + A_R * cos( angle - 1.0 ), y + A_R * sin( angle - 1.0 ) ); //Tail indicates diet. White = carnivore, black = herbivore. // We can also give it a flash of color during significant events. if ( settings.shade ) { if ( fighting && mating > A_C - 5 ) SetColor( Cyan ); //birth else if ( fighting > A_C - 5 ) SetColor( Magenta ); //overcrowding else if ( mating > A_C - 5 ) SetColor( Yellow ); //just married else glColor4f( diet, diet, diet, settings.alpha ); } glVertex2f( x - A_R * cos( angle ), y - A_R * sin( angle ) ); glEnd(); if ( tagged && settings.wake ) { glBegin( GL_LINES ); glColor3f( 1, 1, 1 ); glVertex2f( x-A_R*1.5*cos(angle) + A_R*0.5, y-A_R*1.5*sin(angle) ); if ( settings.shade ) glColor3f( 0, 0, 0 ); glVertex2f( x-A_R*2.0*speed*cos(angle)-A_R*1.5*cos(angle) + A_R*0.5, y-A_R*2.0*speed*sin(angle)-A_R*1.5*sin(angle) ); glColor3f( 1, 1, 1 ); glVertex2f( x-A_R*1.5*cos(angle) - A_R*0.5, y-A_R*1.5*sin(angle) ); if ( settings.shade ) glColor3f( 0, 0, 0 ); glVertex2f( x-A_R*2.0*speed*cos(angle)-A_R*1.5*cos(angle) - A_R*0.5, y-A_R*2.0*speed*sin(angle)-A_R*1.5*sin(angle) ); glColor3f( 1, 1, 1 ); glVertex2f( x-A_R*1.5*cos(angle), y-A_R*1.5*sin(angle) + A_R*0.5 ); if ( settings.shade ) glColor3f( 0, 0, 0 ); glVertex2f( x-A_R*2.0*speed*cos(angle)-A_R*1.5*cos(angle), y-A_R*2.0*speed*sin(angle)-A_R*1.5*sin(angle) + A_R*0.5 ); glColor3f( 1, 1, 1 ); glVertex2f( x-A_R*1.5*cos(angle), y-A_R*1.5*sin(angle) - A_R*0.5 ); if ( settings.shade ) glColor3f( 0, 0, 0 ); glVertex2f( x-A_R*2.0*speed*cos(angle)-A_R*1.5*cos(angle), y-A_R*2.0*speed*sin(angle)-A_R*1.5*sin(angle) - A_R*0.5 ); glEnd(); } } void Animal::RenderEnergy() { float e1, e2; e1 = energy / A_E; if ( e1 > 1.0 ) { e2 = e1 - 1.0; e1 = 1.0; } else e2 = 0.0; glBegin( GL_POLYGON ); glColor3f( 1.0 - e1, e1, 0 ); glVertex2f( -0.76, 0.5 - e1 / 2.1 ); glVertex2f( -0.74, 0.5 - e1 / 2.1 ); if ( settings.shade ) glColor3f( e1, 0, 1.0 - e1 ); glVertex2f( -0.74, 0.5 + e1 / 2.1 ); glVertex2f( -0.76, 0.5 + e1 / 2.1 ); glEnd(); if ( e2 == 0.0 ) return; glBegin( GL_POLYGON ); glColor3f( 1.0 - e2, 0, e2 ); glVertex2f( 0.76, 0.5 - e2 / 2.1 ); glVertex2f( 0.74, 0.5 - e2 / 2.1 ); if ( settings.shade ) glColor3f( e2, 1.0 - e2, 0 ); glVertex2f( 0.74, 0.5 + e2 / 2.1 ); glVertex2f( 0.76, 0.5 + e2 / 2.1 ); glEnd(); } void Animal::See( float d2, Color c, float d, float a ) { float f = 1.0 - ( d2 - A_R * A_R ) / ( A_V * A_V - A_R * A_R ); float da = a - angle; if ( cos( da ) <= 0 ) return; //behind you int i; //Send input to appropriate neuron. // input[0] = plant // input[2] = same // input[4] = prey // input[6] = predator switch( c ) { case P_C: i = 0; break; case Red: switch( color ) { case Red: i = 2; break; case Blue: i = 4; break; case Green: i = 6; break; } break; case Green: switch( color ) { case Green: i = 2; break; case Red: i = 4; break; case Blue: i = 6; break; } break; case Blue: switch( color ) { case Blue: i = 2; break; case Green: i = 4; break; case Red: i = 6; break; } break; } if ( sin( da ) <= sin( A_A ) && sin( da ) >= sin( -A_L ) )//left { brain.input[i].axon += f; } if ( sin( da ) < sin( A_L ) && sin( da ) > sin( -A_A ) )//right { brain.input[i+1].axon += f; } } void Animal::Step() { brain.Think(); //acceleration calculations and normalization goes here x += velocity_x; y += velocity_y; //do bouncing off walls calculations here //other state updates like eating, fitness, etc go here }
# | Change | User | Description | Committed | |
---|---|---|---|---|---|
#15 | 5818 | Sam Stafford | Configurable painter opacity. | ||
#14 | 5096 | Sam Stafford |
Make build work with VS 2003. (No functional change.) |
||
#13 | 4577 | Sam Stafford | Add new "smudge distance" tunable. | ||
#12 | 4572 | Sam Stafford |
New "smudge" feature. REALLY COOL. Off by default (pctsmudge=0) since it's a CPU hog. |
||
#11 | 4452 | Sam Stafford | Fix a couple of small bugs. | ||
#10 | 4451 | Sam Stafford | All significant variables are now user-tweakable. | ||
#9 | 4449 | Sam Stafford | Speed lines, toggle creatures on and off. | ||
#8 | 4448 | Sam Stafford | Turn this thing into a Windows screensaver. | ||
#7 | 4447 | Sam Stafford | Cleanup size-heredity code. | ||
#6 | 4446 | Sam Stafford |
Finished neural inputs, made size hereditary, auto-rotation of images once a certain amount of diffs have been consumed, saving genomes at finish. |
||
#5 | 4441 | Sam Stafford | Ported chase-cam view. | ||
#4 | 4440 | Sam Stafford | Bug fixes, new features, the usual. | ||
#3 | 4439 | Sam Stafford | Hooked the brain up to its muscles, gave the world physics. | ||
#2 | 4433 | Sam Stafford |
More work on this little project. The AI is still nonexistent. |
||
#1 | 4430 | Sam Stafford |
Start importing alife/AI code from Genesaver. Much tweaking will need to be done. |
||
//guest/sam_stafford/genesaver/src/Animal.cpp | |||||
#2 | 3348 | Sam Stafford | Decrease length of tail-color-flashes to 5 timesteps. | ||
#1 | 3052 | Sam Stafford |
Add Genesaver to the Public Depot. It's not in any way Perforce-related, but it does share a bit of code with Jamgraph, and it feels strange to have an open-source project that's not in the PD. |