00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00014
00015 #include "wander.h"
00016
00021
00023
00024 double rand_float() {
00025 const static double rand_max = 0x7fff;
00026 return ((rand()) / (rand_max + 1.0));
00027 }
00028
00034
00036
00037 double random_clamped() {
00038 return (rand_float() - rand_float());
00039 }
00040
00041 Wander::Wander(AICharacter *ai_ch, double wander_radius,int flag, double aoe, float wander_weight) {
00042 _ai_char = ai_ch;
00043 _wander_radius = wander_radius ;
00044 _wander_weight = wander_weight;
00045 double theta = rand_float() * 2 * 3.14159;
00046 double si = rand_float() * 3.14159;
00047 _flag = flag;
00048
00049 _area_of_effect = aoe;
00050 _init_pos = _ai_char->get_node_path().get_pos(_ai_char->get_char_render());
00051
00052
00053
00054
00055
00056
00057 switch(_flag) {
00058 case 0: {
00059 _wander_target = LVecBase3f(_wander_radius * cos(theta), _wander_radius * sin(theta),0);
00060 break;
00061 }
00062 case 1: {
00063 _wander_target = LVecBase3f(0, _wander_radius * cos(theta), _wander_radius * sin(theta));
00064 break;
00065 }
00066 case 2: {
00067 _wander_target = LVecBase3f(_wander_radius * cos(theta), 0, _wander_radius * sin(theta));
00068 break;
00069 }
00070 case 3: {
00071 _wander_target = LVecBase3f(_wander_radius * sin(theta) * cos(si), _wander_radius * sin(theta) * sin(si), _wander_radius * cos(theta));
00072 break;
00073 }
00074 default: {
00075 _wander_target = LVecBase3f(_wander_radius * cos(theta), _wander_radius * sin(theta),0);
00076 break;
00077 }
00078 }
00079 }
00080
00081 Wander::~Wander() {
00082 }
00083
00090
00092
00093 LVecBase3f Wander::do_wander() {
00094 LVecBase3f present_pos = _ai_char->get_node_path().get_pos(_ai_char->get_char_render());
00095
00096 double time_slice_1 = random_clamped() * 1.5;
00097 double time_slice_2 = random_clamped() * 1.5;
00098 double time_slice_3 = random_clamped() * 1.5;
00099 switch(_flag) {
00100 case 0: {
00101 _wander_target += LVecBase3f(time_slice_1, time_slice_2, 0);
00102 break;
00103 }
00104 case 1: {
00105 _wander_target += LVecBase3f(0, time_slice_1, time_slice_2);
00106 break;
00107 }
00108 case 2: {
00109 _wander_target += LVecBase3f(time_slice_1, 0, time_slice_2);
00110 break;
00111 }
00112 case 3: {
00113 _wander_target += LVecBase3f(time_slice_1, time_slice_2, time_slice_3);
00114 break;
00115 }
00116
00117 default: {
00118 _wander_target = LVecBase3f(time_slice_1, time_slice_2, 0);
00119 }
00120 }
00121 _wander_target.normalize();
00122 _wander_target *= _wander_radius;
00123 LVecBase3f target = _ai_char->get_char_render().get_relative_vector(_ai_char->get_node_path(), LVector3f::forward());
00124 target.normalize();
00125
00126 target = _wander_target + target;
00127 LVecBase3f desired_target = present_pos + target;
00128 LVecBase3f desired_force = desired_target - _ai_char->get_node_path().get_pos() ;
00129 desired_force.normalize();
00130 desired_force *= _ai_char->_movt_force;
00131 double distance = (present_pos - _init_pos).length();
00132 if(_area_of_effect > 0 && distance > _area_of_effect) {
00133 LVecBase3f direction = present_pos - _init_pos;
00134 direction.normalize();
00135 desired_force = - direction * _ai_char->_movt_force;
00136 LVecBase3f dirn = _ai_char->_steering->_steering_force;
00137 dirn.normalize();
00138 _ai_char->_steering->_steering_force = LVecBase3f(0.0, 0.0, 0.0);
00139 }
00140 return desired_force;
00141 }