Expert
Joined: Feb 2008
Posts: 3,232
Australia
|
Got him at last, USE_AABB flag be-damned! Code looks horrible in the forum windows, but just copy and paste into SED and it will look fine. Minimal changes in my opinion. Thoroughly test please, as many versions of 3DGS as possible. Main.C #include <acknex.h>
#include <default.c>
#include "player.c"
#include "enemy.c"
#include "animation.c"
function main()
{
camera.clip_near = 0;
video_switch(7,0,1);
level_load("level.wmb");
} player.C function rotate_entity(var rotate_angle, var rotate_speed);
function handle_gravity();
function handle_movement();
function handle_camera();
function handle_animation(var animation_speed);
#define nullframe -2
#define blend -1
#define stand 0
#define run 1
#define walk 2
#define jump 3
#define fall 4
#define attack_a 5
#define attack_b 6
#define attack_c 7
#define attack_d 8
#define attack_e 9
#define attack_f 10
#define move_x skill22
#define move_y skill23
#define move_z skill24
#define force_x skill25
#define force_y skill26
#define force_z skill27
#define velocity_x skill28
#define velocity_y skill29
#define velocity_z skill30
#define animate skill31
#define animate2 skill32
#define animblend skill33
#define currentframe skill34
#define blendframe skill35
#define z_offset skill50
#define jumping_mode skill51
#define gravity skill52
#define movement_mode skill53
#define moving skill54
#define hit_by_player skill55
#define entity_type skill56
ENTITY* player_weapon;
ENTITY* target_enemy;
var temp;
VECTOR* tempV = { x=0; y=0; z=0; }
VECTOR* tempV2= { x=0; y=0; z=0; }
ANGLE* tempA = { pan=0; tilt=0; roll=0; }
ANGLE* tempA2= { pan=0; tilt=0; roll=0; }
VECTOR* camera_move_to = { x=0; y=0; z=0; }
var camera_distance = 200;
var camera_pan;
var camera_tilt;
var space_press = 0;
var mouse_left_press = 0;
var mouse_right_press = 0;
var combo_continue = 0;
var player_lock_on = 0;
var airborne_attack = 0;
action attach_weapon()
{
player_weapon = my;
set(my,PASSABLE);
proc_mode = PROC_LATE;
while(you != NULL)
{
vec_for_vertex(tempV.x, you, 1175); //hand palm base
vec_for_vertex(tempV2.x, you, 1240); //hand palm tip
vec_set(my.x, tempV.x);
vec_diff(tempV.x, tempV2.x, tempV.x);
vec_to_angle(tempA.pan, tempV.x);
vec_set(my.pan, tempA.pan);
wait(1);
}
}
action player_action()
{
player = my;
my.gravity = 6;
my.z_offset = 12;
set(my,SHADOW);
ent_create("sword.mdl", my.x, attach_weapon);
wait(1);
while(1)
{ //the main player loop
handle_gravity();
handle_movement();
handle_camera();
handle_animation(1);
wait(1);
}
}
function handle_movement()
{
tempV.x = -1000;
tempV.y = 0;
my.moving = 0;
if(key_w == 1 && key_s == 0 && key_a == 0 && key_d == 0) tempV.x = camera.pan;
if(key_s == 1 && key_w == 0 && key_a == 0 && key_d == 0) tempV.x = camera.pan + 180;
if(key_a == 1 && key_s == 0 && key_w == 0 && key_d == 0) tempV.x = camera.pan + 90;
if(key_d == 1 && key_s == 0 && key_a == 0 && key_w == 0) tempV.x = camera.pan - 90;
if(key_w == 1 && key_a == 1 && key_d == 0 && key_s == 0) tempV.x = camera.pan + 45;
if(key_w == 1 && key_d == 1 && key_a == 0 && key_s == 0) tempV.x = camera.pan - 45;
if(key_s == 1 && key_a == 1 && key_d == 0 && key_w == 0) tempV.x = camera.pan + 135;
if(key_s == 1 && key_d == 1 && key_a == 0 && key_w == 0) tempV.x = camera.pan - 135;
if(tempV.x != -1000)
{
my.moving = 1;
if(key_shift == 1) tempV.y = 10 * time_step;
else tempV.y = 15 * time_step;
}
//
if(my.movement_mode==0)
{
my.move_x = fcos(tempV.x, tempV.y);
my.move_y = fsin(tempV.x, tempV.y);
}
else if((my.movement_mode==1)||(my.movement_mode==2))
{
tempV.y = fsin((my.animate * 1.2) + 45,15 * time_step);
my.move_x = fcos(my.pan, tempV.y);
my.move_y = fsin(my.pan, tempV.y);
tempV.y = 0;
//NextLine: if we need to rotate whilst attacking (the player is pressing keys to rotate)
if(tempV.x != -1000) tempV.y = 1;
}
//
c_move(my, nullvector, my.move_x, USE_BOX | IGNORE_PASSABLE | GLIDE);
result = -my.z_offset + c_trace(vector(my.x,my.y,my.z - my.z_offset), vector(my.x,my.y,my.z - 4000), IGNORE_ME | IGNORE_PASSABLE | USE_BOX);
result = clamp(result, -50, 50);
if(result < 0) { my.z -= result; my.velocity_z = 0; }
//
if(target_enemy == NULL)
{ if(tempV.y > 0) rotate_entity(tempV.x, 30); }
else
{
vec_diff(tempV2.x, target_enemy.x, my.x);
vec_to_angle(tempA2.pan, tempV2.x);
rotate_entity(tempA2.pan,30);
}
//
if(my.movement_mode == 0)
{
my.gravity = 6;
if(my.move_x != 0 || my.move_y != 0)
{ //ifwe are moving
if(my.animblend == stand)
{ //ifour current animation is stand
if(key_shift == 1) my.blendframe = walk;
else my.blendframe = run;
}
if(my.animblend == run && key_shift == 1) my.blendframe = walk;
if(my.animblend == walk && key_shift == 0) my.blendframe = run;
}
else
{
if(my.animblend > stand && my.animblend != jump && my.animblend != fall)
{ //if we arn't moving and our current animation is walk or run, blend and cycle the stand animation
my.blendframe = stand;
}
}
if(mouse_left == 0 && mouse_left_press == 1) mouse_left_press = 0;
if(mouse_left == 1 && mouse_left_press == 0 && my.animblend >= stand)
{
mouse_left_press = 1;
my.blendframe = attack_a;
if(my.jumping_mode == 1) airborne_attack = 1;
else airborne_attack = 0;
my.movement_mode = 1;
combo_continue = 0;
}
if(mouse_right == 0 && mouse_right_press == 1) mouse_right_press = 0;
if(mouse_right == 1 && mouse_right_press == 0)
{
if(player_lock_on == 0)
{
c_scan(player.x, player.pan, vector(360,180,250), SCAN_ENTS | SCAN_LIMIT | IGNORE_ME);
if(you != NULL)
{
if(you.entity_type == 2)
{ //make sure you've scanned an enemy
player_lock_on = 1;
target_enemy = you;
}
}
}
else
{
player_lock_on = 0;
target_enemy = NULL;
}
mouse_right_press = 1;
}
}
//
if(my.movement_mode == 1)
{
if(my.jumping_mode != 10) my.jumping_mode = 0;
else if(my.animate >= 60 && my.animblend >= stand) my.jumping_mode = 0;
//
if(mouse_left == 0 && mouse_left_press == 1)
mouse_left_press = 0;
if(mouse_left == 1 && mouse_left_press == 0 && my.animate >= 30 && combo_continue == 0)
{ mouse_left_press = 1; combo_continue = 1; }
}
//
if(my.movement_mode == 2)
{
my.jumping_mode = 0;
if(mouse_left == 0 && mouse_left_press == 1)
mouse_left_press = 0;
if(mouse_left == 1 && mouse_left_press == 0 && my.animate >= 30 && combo_continue == 0)
{ mouse_left_press = 1; combo_continue = 1; }
}
}
function handle_gravity()
{
result = -my.z_offset + c_trace(vector(my.x,my.y,my.z - my.z_offset), vector(my.x,my.y,my.z - 4000), IGNORE_ME | IGNORE_PASSABLE | USE_BOX );
result = clamp(result, -50, 50);
if(result < 3)
{
if(my.jumping_mode == 0)
{
my.force_z = -1 * result;
if(key_space == 0 && space_press == 1) space_press = 0;
if(key_space == 1 && space_press == 0 && my.movement_mode == 0 && my.animblend >= stand && my.animblend != jump && my.animblend != fall)
{
space_press = 1;
my.jumping_mode = 1;
my.force_z = 25;
my.blendframe = jump;
my.animate2 = 0;
my.animblend = blend;
}
}
if(my.jumping_mode == 2 || my.jumping_mode == 3) my.jumping_mode = 0;
}
else
{
if(my.jumping_mode == 2)
{
if(result > 120)
{
my.animate = 60;
my.jumping_mode = 3;
}
else
my.jumping_mode = 0;
}
if(my.jumping_mode == 3 && result <= 120) my.jumping_mode = 0;
if(my.jumping_mode == 0 && my.movement_mode == 0)
{
if(result > 120 && my.animblend >= stand && my.animblend != jump && my.animblend != fall)
{
my.jumping_mode = 3;
my.blendframe = fall;
my.animate2 = 0;
my.animblend = blend;
}
}
my.force_z -= my.gravity * time_step;
my.force_z = maxv(-30, my.force_z);
if(my.movement_mode == 2) my.force_z = 0;
}
my.velocity_z += (time_step * my.force_z) - (minv(time_step*0.7, 1) * my.velocity_z);
my.move_z = my.velocity_z * time_step;
}
//////////////////////////////
//Stable/rigid camera collision
//////////////////////////////
function handle_camera()
{
camera.pan -= mouse_force.x * 12 * time_step;
camera.tilt += mouse_force.y * 8 * time_step;
camera.tilt = clamp(camera.tilt, -30, 10);
temp = fcos(camera.tilt, -camera_distance);
vec_set(camera.x, vector(my.x + fcos(camera.pan, temp),my.y + fsin(camera.pan, temp),my.z + 20 + fsin(camera.tilt, -camera_distance)));
vec_diff(tempV.x, camera.x, my.x); //find the vector from the player to the camera
vec_normalize(tempV.x, 16); //get the magnitude of it's vector to 16 quants and store it in temp
vec_add(tempV.x, camera.x); //add the vector (from player to camera) of a magnitude of 16 quants and add it to the camera's position.
result = c_trace(my.x, tempV.x, IGNORE_ME|IGNORE_PASSABLE|IGNORE_MODELS); //trace from the player to 16 quants behind the camera.
if(result > 0)
{
vec_diff(tempV.x, my.x, target.x); //find the vector from the point the trace hit to the player
vec_normalize(tempV.x, 16); //get the magnitude of this vector to 16 quants and store in temp
vec_set(camera.x, target.x); //place the camera at the trace hit point
vec_add(camera.x, tempV.x); //move the camera away from the wall by the vector temp, 16 quants towards the player
}
}
//////////////////////////////
//Smooth camera collision
//////////////////////////////
/*function handle_camera()
{
camera_pan -= mouse_force.x * 12 * time_step;
camera_tilt += mouse_force.y * 8 * time_step;
camera_tilt = clamp(camera_tilt, -30, 10);
camera.pan = camera_pan;
temp = fcos(camera_tilt,-camera_distance);
vec_set(camera_move_to.x, vector(my.x + fcos(camera.pan, temp), my.y + fsin(camera.pan, temp), my.z + 20 + fsin(camera_tilt, -camera_distance)));
temp = minv(1,0.5 * time_step); //changing 0.5 will change how fast the camera moves, at 1 places us at target, this value is what allows the smooth movement
camera.x += temp*(camera_move_to.x - camera.x);
camera.y += temp*(camera_move_to.y - camera.y);
camera.z += temp*(camera_move_to.z - camera.z);
vec_diff(tempV.x, camera.x, my.x);
vec_normalize(tempV.x, 16);
vec_add(tempV.x, camera.x);
if(c_trace(my.x, tempV.x, IGNORE_ME|IGNORE_PASSABLE|IGNORE_MODELS) > 0)
{
vec_diff(tempV.x, my.x, target.x);
vec_normalize(tempV.x, 16);
vec_set(camera.x, target.x);
vec_add(camera.x, tempV.x);
}
vec_diff(tempV.x, my.x, camera.x);
vec_to_angle(camera.pan, tempV.x);
}*/
function rotate_entity(var rotate_angle, var rotate_speed)
{
if(my.pan == rotate_angle) return;
result = ang(rotate_angle - my.pan);
if(result > 0) my.pan += rotate_speed * time_step;
if(result < 0) my.pan -= rotate_speed * time_step;
if(ang(rotate_angle - my.pan) < 0 && result > 0) my.pan = rotate_angle;
if(ang(rotate_angle - my.pan) > 0 && result < 0) my.pan = rotate_angle;
}
function handle_sword_collision()
{
you = NULL;
vec_for_vertex(tempV.x, player_weapon, 274); //sword base
vec_for_vertex(tempV2.x, player_weapon, 54); //sword tip
result = c_trace(tempV.x, tempV2.x, IGNORE_ME | IGNORE_PASSABLE | USE_BOX);
if(you != NULL)
{
if(you.entity_type == 2 && you.hit_by_player == 0)
{
if(airborne_attack == 1 && my.animblend == attack_a) my.movement_mode = 2;
you.hit_by_player = 1;
if(target_enemy == NULL) { target_enemy = you; player_lock_on = 1; }
}
}
} enemy.C action enemy_dummy()
{
set(my,SHADOW);
my.entity_type = 2;
my.emask |= ENABLE_SCAN;
while(1)
{
if(my.hit_by_player == 1)
{
my.move_x = player.move_x;
my.move_y = player.move_y;
my.move_z = player.move_z;
c_move(my, nullvector, my.move_x, USE_BOX | IGNORE_PASSABLE | GLIDE);
if(player.animblend == blend || player.animblend < attack_a || my.animblend > attack_f) my.hit_by_player = 0;
}
if((player.animblend >= stand && target_enemy == me && player_lock_on == 0) && (player.animblend < attack_a || player.animblend > attack_f))
target_enemy = NULL;
if(target_enemy == my && vec_dist(my.x, player.x) > 200)
target_enemy = NULL;
wait(1);
}
} animation.C function handle_animation(var animation_speed)
{
if(animation_speed <= 0) animation_speed = 1;
if(my.animblend != blend && my.blendframe != nullframe) { my.animate2 = 0; my.animblend = blend; }
if(my.animblend == blend)
{
if (my.currentframe == stand) ent_animate(my, "stand", my.animate, ANM_CYCLE);
else if(my.currentframe == run) ent_animate(my, "run", my.animate, ANM_CYCLE);
else if(my.currentframe == walk) ent_animate(my, "walk", my.animate, ANM_CYCLE);
else if(my.currentframe == jump) ent_animate(my, "jump", my.animate,0);
else if(my.currentframe == attack_a) ent_animate(my, "attack_a", my.animate,0);
else if(my.currentframe == attack_b) ent_animate(my, "attack_b", my.animate,0);
else if(my.currentframe == attack_c) ent_animate(my, "attack_c", my.animate,0);
else if(my.currentframe == attack_d) ent_animate(my, "attack_d", my.animate,0);
else if(my.currentframe == attack_e) ent_animate(my, "attack_e", my.animate,0);
else if(my.currentframe == attack_f) ent_animate(my, "attack_f", my.animate,0);
if (my.blendframe == stand) ent_blend("stand",0,my.animate2);
else if(my.blendframe == run) ent_blend("run",0,my.animate2);
else if(my.blendframe == walk) ent_blend("walk",0,my.animate2);
else if(my.blendframe == jump) ent_blend("jump",0,my.animate2);
else if(my.blendframe == fall) ent_blend("jump",60,my.animate2);
else if(my.blendframe == attack_a) ent_blend("attack_a",0,my.animate2);
else if(my.blendframe == attack_b) ent_blend("attack_b",0,my.animate2);
else if(my.blendframe == attack_c) ent_blend("attack_c",0,my.animate2);
else if(my.blendframe == attack_d) ent_blend("attack_d",0,my.animate2);
else if(my.blendframe == attack_e) ent_blend("attack_e",0,my.animate2);
else if(my.blendframe == attack_f) ent_blend("attack_f",0,my.animate2);
my.animate2 += 45 * time_step;
if(my.animate2 >= 100)
{
my.animate = 0;
my.animblend = my.blendframe;
my.blendframe = nullframe;
}
}
//
switch(my.animblend)
{
case stand:
ent_animate(my,"stand",my.animate,ANM_CYCLE);
my.animate += 5 * animation_speed * time_step;
my.animate %= 100;
my.currentframe = stand;
break;
case run:
ent_animate(my,"run",my.animate,ANM_CYCLE);
my.animate += 8 * animation_speed * time_step;
my.animate %= 100;
my.currentframe = run;
break;
case walk:
ent_animate(my,"walk",my.animate,ANM_CYCLE);
my.animate += 8 * animation_speed * time_step;
my.animate %= 100;
my.currentframe = walk;
break;
case jump: //flow through to fall
case fall:
if(my.jumping_mode == 3) { my.animate = 60; }
ent_animate(my,"jump",my.animate,0);
my.animate += 10 * animation_speed * time_step;
my.currentframe = jump;
if(my.animate >= 60 && my.jumping_mode == 1) my.jumping_mode = 2;
if(my.animate >= 100)
{
ent_animate(my,"jump",100,0);
my.animate = 100;
my.blendframe = stand;
if(my.moving == 1)
{
if(key_shift == 1) my.blendframe = walk;
else my.blendframe = run;
}
}
break;
case attack_a:
ent_animate(my,"attack_a",my.animate,0);
my.animate += 20 * animation_speed * time_step;
my.currentframe = attack_a;
if(my.animate >= 100)
{
ent_animate(my,"attack_a",100,0);
my.animate = 100;
my.blendframe = stand;
if(my.moving == 1)
{
if(key_shift == 1) my.blendframe = walk;
else my.blendframe = run;
}
if(combo_continue == 1)
{
combo_continue = 0;
my.blendframe = attack_b;
}
else
my.movement_mode = 0;
}
break;
case attack_b:
ent_animate(my,"attack_b",my.animate,0);
my.animate += 15 * animation_speed * time_step;
my.currentframe = attack_b;
if(my.animate >= 100)
{
ent_animate(my,"attack_b",100,0);
my.animate = 100;
my.blendframe = stand;
if(my.moving == 1)
{
if(key_shift == 1) my.blendframe = walk;
else my.blendframe = run;
}
if(combo_continue == 1)
{
combo_continue = 0;
my.blendframe = attack_c;
}
else
my.movement_mode = 0;
}
break;
case attack_c:
ent_animate(my,"attack_c",my.animate,0);
my.animate += 10 * animation_speed * time_step;
my.currentframe = attack_c;
if(my.animate >= 100)
{
ent_animate(my,"attack_c",100,0);
my.animate = 100;
my.blendframe = stand;
if(my.moving == 1)
{
if(key_shift == 1) my.blendframe = walk;
else my.blendframe = run;
}
if(combo_continue == 1)
{
my.jumping_mode = 10;
my.force_z = 12;
my.gravity = 4;
combo_continue = 0;
my.blendframe = attack_d;
}
else
my.movement_mode = 0;
}
break;
case attack_d:
handle_sword_collision();
ent_animate(my,"attack_d",my.animate,0);
my.animate += 15 * animation_speed * time_step;
my.currentframe = attack_d;
if(my.animate >= 100)
{
ent_animate(my,"attack_d",100,0);
my.animate = 100;
my.blendframe = stand;
if(my.moving == 1)
{
if(key_shift == 1) my.blendframe = walk;
else my.blendframe = run;
}
if(combo_continue == 1)
{
combo_continue = 0;
my.blendframe = attack_e;
}
else
my.movement_mode = 0;
}
break;
case attack_e:
ent_animate(my,"attack_e",my.animate,0);
my.animate += 15 * animation_speed * time_step;
my.currentframe = attack_e;
if(my.jumping_mode == 0 && my.animate >= 20 && my.animate < 60)
{
my.gravity = 3;
my.jumping_mode = 10;
my.force_z = 15;
}
if(my.animate >= 100)
{
ent_animate(my,"attack_e",100,0);
my.animate = 100;
my.blendframe = stand;
if(my.moving == 1)
{
if(key_shift == 1) my.blendframe = walk;
else my.blendframe = run;
}
if(combo_continue == 1)
{
combo_continue = 0;
my.blendframe = attack_f;
}
else
my.movement_mode = 0;
}
break;
case attack_f:
ent_animate(my,"attack_f",my.animate,0);
my.animate += 6 * animation_speed * time_step;
my.currentframe = attack_f;
if(my.jumping_mode == 0 && my.animate >= 40 && my.animate < 60)
{
my.gravity = 6;
my.jumping_mode = 10;
my.force_z = 12;
}
if(my.animate >= 100)
{
my.movement_mode = 0;
ent_animate(my,"attack_f",100,0);
my.animate = 100;
my.blendframe = stand;
if(my.moving == 1)
{
if(key_shift == 1) my.blendframe = walk;
else my.blendframe = run;
}
}
break;
}
if(my.animblend >= attack_a && my.animblend <= attack_f) handle_sword_collision();
if(my.animblend != blend && my.blendframe != nullframe) { my.animate2 = 0; my.animblend = blend; }
}
Last edited by EvilSOB; 02/13/09 14:00. Reason: Code bug corrected!
"There is no fate but what WE make." - CEO Cyberdyne Systems Corp. A8.30.5 Commercial
|