コード例 #1
0
ファイル: sx3_engine.c プロジェクト: cout/sx3
// init_scene initializes the global variable g_projectiles immediately after
// a shot has been fired.
void init_scene()
{
    struct Tank *t = &g_tanks[g_current_tank];
    Vector dir = {
        sin(D2R(t->s.turret_angle))*cos(D2R(t->s.weapon_angle)),
        sin(D2R(t->s.weapon_angle)),
        cos(D2R(t->s.turret_angle))*cos(D2R(t->s.weapon_angle)),
    };
    Vector pos;

    // FIX ME!! Is this the right way to handle tank angle?
    // vv_add(dir, t->o.props.angular_position);
    v_norm(dir);

    // FIX ME!! We do not fire from the end of the barrel
    vv_cpy(pos, t->o.props.position);
    vv_add(pos, t->m.turret_base);
    vv_add(pos, t->m.weapon_base);

    printf("New projectile\n");
    printf("Position: %f %f %f\n", pos[0], pos[1], pos[2]);
    printf("Direction: %f %f %f\n", dir[0], dir[1], dir[2]);
    printf("Tank pos: %f %f %f\n",
        t->o.props.position[0], t->o.props.position[1], t->o.props.position[2]);

    new_projectile(
        dir,                                // Direction
        t->s.power,                         // Magnitude
        pos,                                // Position
        Missile_I                           // Type
    );
}
コード例 #2
0
void move_particle(particle_type* p, GLfloat delta) {
   Vector accel, tempa, tempv;
   GLfloat deltasq = delta*delta;
   accel[0] = 0.0; accel[1] = -ps->gravity; accel[2] = 0.0; accel[3] = 0.0;
   vv_cpy(tempa, accel);
   vc_mul(tempa, 0.5);
   vc_mul(tempa, deltasq);
   vv_cpy(tempv, p->velocity);
   vc_mul(tempv, (double)delta);
   vv_add(tempa, tempv);
   vv_cpy(p->prevpos[p->begin], p->position);
   p->begin = (p->begin + 1) % PREVIOUS;
   vv_add(p->position, tempa);
   vv_cpy(tempa, accel);
   vc_mul(tempa, delta);
   vv_add(p->velocity, tempa);
}
コード例 #3
0
void initparticle(particle_type* p) {
   p->position[0] = ps->initpos[0];
   p->position[1] = ps->initpos[1];
   p->position[2] = ps->initpos[2];
   p->position[3] = 0.0;
   v_zero(p->velocity);
   p->color[0] = 1.0;
   p->color[1] = 1.0;
   p->color[2] = 1.0;
   p->color[3] = 0.0;
   vv_cpy(p->prevpos[0], p->position);
   vv_cpy(p->prevpos[1], p->position);
   vv_cpy(p->prevpos[2], p->position);
   vv_cpy(p->prevpos[3], p->position);
   vv_cpy(p->prevpos[4], p->position);
   p->begin = 0;
}
コード例 #4
0
int draw_3d_tri(
	pVector v1p, Graph3dColor c1p, pVector n1p,
	pVector v2p, Graph3dColor c2p, pVector n2p,
	pVector v3p, Graph3dColor c3p, pVector n3p) {

	int j;
	int x1, x2, x3;
	int y1, y2, y3;

	// First, convert the colors to floats
	Vector c1 = {
		(float)c1p.r / 255.0,
		(float)c1p.g / 255.0,
		(float)c1p.b / 255.0,
		1.0
	};
	Vector c2 = {
		(float)c2p.r / 255.0,
		(float)c2p.g / 255.0,
		(float)c2p.b / 255.0,
		1.0
	};
	Vector c3 = {
		(float)c3p.r / 255.0,
		(float)c3p.g / 255.0,
		(float)c3p.b / 255.0,
		1.0
	};

	Vector v1, v2, v3;
	Vector n1, n2, n3;
	Vector L1, L2, L3;

	// Next, apply the modelview matrix to the triangle's vertices
	vv_cpy(v1, v1p); vv_cpy(v2, v2p); vv_cpy(v3, v3p);
	vm_mul(v1, modelview);
	vm_mul(v2, modelview);
	vm_mul(v3, modelview);

	// And also to the normals
	vv_cpy(n1, n1p); vv_cpy(n2, n2p); vv_cpy(n3, n3p);
	vm_mul(n1, modelview);
	vm_mul(n2, modelview);
	vm_mul(n3, modelview);

	// Find the distance for each point from the light
	vv_cpy(L1, lightpos); vv_sub(L1, v1); v_norm(L1);
	vv_cpy(L2, lightpos); vv_sub(L2, v2); v_norm(L2);
	vv_cpy(L3, lightpos); vv_sub(L3, v3); v_norm(L3);

	// Then, apply our lighting equations
	// We assume that the triangle's ambient and diffuse values are the same
	// We also assume that 
	for(j = 0; j < 4; j++) {
		c1[j] = light_transform(c1[j], n1, L1, j);
		c2[j] = light_transform(c2[j], n2, L2, j);
		c2[j] = light_transform(c3[j], n3, L3, j);
	}

	// Convert the color values to values the graphics card will accept
	// c1p et al were passed by value, so we can modify them
	c1p.r = c1[0] * 255;
	c1p.g = c1[1] * 255;
	c1p.b = c1[2] * 255;
	c2p.r = c2[0] * 255;
	c2p.g = c2[1] * 255;
	c2p.b = c2[2] * 255;
	c3p.r = c3[0] * 255;
	c3p.g = c3[1] * 255;
	c3p.b = c3[2] * 255;

	// Lastly, find the coordinates on the screen for each point,
	// and draw the triangle
	x1 = 800 * (depth/height) * (v1[0] / v1[2]);
	y1 = 600 * (depth/height) * (v1[1] / v1[2]);
	x2 = 800 * (depth/height) * (v2[0] / v2[2]);
	y2 = 600 * (depth/height) * (v2[1] / v2[2]);
	x3 = 800 * (depth/height) * (v3[0] / v3[2]);
	y3 = 600 * (depth/height) * (v3[1] / v3[2]);
	draw_2d_tri(x1, y1, c1p, x2, y2, c2p, x3, y3, c3p);

	printf("v1: %f %f %f\n", v1[0], v1[1], v1[2]);
	printf("v2: %f %f %f\n", v2[0], v2[1], v2[2]);
	printf("v2: %f %f %f\n", v3[0], v3[1], v3[2]);
	printf("%d %d; %d %d; %d %d\n", x1, y1, x2, y2, x3, y3);

	return GRAPH3D_OK;
}
コード例 #5
0
int graph3d_set_lightpos(pVector v) {
	vv_cpy(lightpos, v);
	return GRAPH3D_OK;
}
コード例 #6
0
ファイル: sx3_engine.c プロジェクト: cout/sx3
// modify_scene modifies the global variables g_projectiles and g_explosions
// during the course of an attack sequence.  It takes a parameter dt which
// represents the amount of time between frames.
// Return: the number of items left to animate.
int modify_scene(float dt)
{
    int i, j, num_impacted;
    float t;
    struct Projectile *p;
    struct Explosion *e;
    struct Tank *tank;
    Vector v;
    float d;

    // Go through all the explosions and update them according to the
    // amount of time passed.
    for(j = 0; j < g_num_explosions; j++)
    {
        e = &g_explosions[j];
        t = update_explosion(e, dt);
    }

    // Go through all the projectiles and handle the ones that have not yet
    // been impacted.
    for(j = 0, num_impacted = 0; j < g_num_projectiles; j++)
    {
        p = &g_projectiles[j];
        if(p->o.state != STATE_IMPACTED)
        {
            t = update_projectile(p, dt);
            if(p->o.state == STATE_IMPACTED)
            {
                printf("Projectile %d has impacted.\n", j);
                // If the projectile has impacted, an explosion needs to be
                // created which is appropriate to the projectile which has
                // impacted, and which takes on properties of the former
                // projectile.
                e = new_explosion(p);

                // Now, using the remaining time that did not get used on the
                // projectile, update the new explosion.
                t = update_explosion(e, dt - t);

                // And play a sound to match
                sx3_play_sound(SX3_AUDIO_EXPLOSION);
            }
        }
        if(p->o.state == STATE_IMPACTED) num_impacted++;
    }

    // FIX ME!! These two checks don't work properly if we have a low
    // framerate.
    for(j = 0; j < g_num_explosions; j++)
    {
        e = &g_explosions[j];
        for(i = 0; i < g_num_tanks; i++)
        {
            tank = &g_tanks[i];
            // Don't check this tank if it's already been hit
            // FIX ME!! This should be on a per-projectile/explosion basis
            if(tank->s.temp_damage != 0.0) continue;

            // Find the distance between the tank and the explosion, and test
            vv_cpy(v, tank->o.props.position);
            vv_sub(v, e->props.position);
            d = v_mag(v);

            if(d < tank->o.props.radius + e->props.radius)
            {
                // A tank has been hit!
                sx3_play_sound(SX3_AUDIO_HIT);
                printf("Tank %d hit by explosion %d\n", i, j);
                // FIX ME!! This should not be constant damage.
                tank->s.temp_damage = 20.0;
            }
        }
    }

    for(j = 0; j < g_num_projectiles; j++)
    {
        p = &g_projectiles[j];
        if(p->o.state == STATE_IMPACTED) continue;
        for(i = 0; i < g_num_tanks; i++)
        {
            tank = &g_tanks[i];
            // Don't check this tank if it's already been hit
            // FIX ME!! This should be on a per-projectile/explosion basis
            if(tank->s.temp_damage != 0.0) continue;

            // Find the distance between the tank and the projectiles, and test
            vv_cpy(v, tank->o.props.position);
            vv_sub(v, p->o.props.position);
            d = v_mag(v);

            if(d < tank->o.props.radius + p->o.props.radius)
            {
                // A tank has been hit!
                sx3_play_sound(SX3_AUDIO_HIT);
                printf("Tank %d hit by projectile %d\n", i, j);
                // FIX ME!! This should not be constant damage.
                tank->s.temp_damage = 40.0;
            }
        }
    }
    return g_num_explosions + g_num_projectiles - num_impacted;
}