diff --git a/src/karts/kart_model.cpp b/src/karts/kart_model.cpp index 1f07c4219..f40a37f48 100755 --- a/src/karts/kart_model.cpp +++ b/src/karts/kart_model.cpp @@ -32,18 +32,18 @@ float KartModel::UNDEFINED = -99.9f; */ KartModel::KartModel() { - for(unsigned int i=0; i<4; i++) - { - m_wheel_graphics_position[i] = Vec3(UNDEFINED); - m_wheel_physics_position[i] = Vec3(UNDEFINED); - m_wheel_graphics_radius[i] = 0.0f; // for kart without separate wheels - m_wheel_model[i] = NULL; - m_min_suspension[i] = -99.9f; - m_max_suspension[i] = 99.9f; - } - m_wheel_filename[0] = "wheel-front-right.ac"; - m_wheel_filename[1] = "wheel-front-left.ac"; - m_wheel_filename[2] = "wheel-rear-right.ac"; + for(unsigned int i=0; i<4; i++) + { + m_wheel_graphics_position[i] = Vec3(UNDEFINED); + m_wheel_physics_position[i] = Vec3(UNDEFINED); + m_wheel_graphics_radius[i] = 0.0f; // for kart without separate wheels + m_wheel_model[i] = NULL; + m_min_suspension[i] = -99.9f; + m_max_suspension[i] = 99.9f; + } + m_wheel_filename[0] = "wheel-front-right.ac"; + m_wheel_filename[1] = "wheel-front-left.ac"; + m_wheel_filename[2] = "wheel-rear-right.ac"; m_wheel_filename[3] = "wheel-rear-left.ac"; m_root = NULL; @@ -56,11 +56,11 @@ KartModel::KartModel() */ void KartModel::loadInfo(const lisp::Lisp* lisp) { - lisp->get("model-file", m_model_filename); - loadWheelInfo(lisp, "wheel-front-right", 0); - loadWheelInfo(lisp, "wheel-front-left", 1); - loadWheelInfo(lisp, "wheel-rear-right", 2); - loadWheelInfo(lisp, "wheel-rear-left", 3); + lisp->get("model-file", m_model_filename); + loadWheelInfo(lisp, "wheel-front-right", 0); + loadWheelInfo(lisp, "wheel-front-left", 1); + loadWheelInfo(lisp, "wheel-rear-right", 2); + loadWheelInfo(lisp, "wheel-rear-left", 3); } // init // ---------------------------------------------------------------------------- /** Destructor. @@ -70,7 +70,7 @@ KartModel::~KartModel() // This automatically frees the wheels and the kart model. // m_root can be zero in case of STKConfig, which has a kart_properties // attribute (for the default values) as well. - if(m_root) m_root->removeAllKids(); + if(m_root) m_root->removeAllKids(); ssgDeRefDelete(m_root); } // ~KartModel @@ -79,31 +79,31 @@ KartModel::~KartModel() */ void KartModel::loadModels() { - ssgEntity *obj = loader->load(m_model_filename, CB_KART); - if(!obj) - { - fprintf(stderr, "Can't find kart model '%s'.\n",m_model_filename.c_str()); - return; - } - m_root = new ssgTransform(); - m_root->ref(); - m_root->addKid(obj); - ssgStripify(obj); - Vec3 min, max; - SSGHelp::MinMax(obj, &min, &max); - m_z_offset = min.getZ(); - m_kart_width = max.getX()-min.getX(); - m_kart_length = max.getY()-min.getY(); - m_kart_height = max.getZ()-min.getZ(); - sgVec3 move_kart_to_0_z; - sgSetVec3(move_kart_to_0_z, 0, 0, m_z_offset); - m_root->setTransform(move_kart_to_0_z); - - // Now set default some default parameters (if not defined) that - // depend on the size of the kart model (wheel position, center - // of gravity shift) - for(unsigned int i=0; i<4; i++) - { + ssgEntity *obj = loader->load(m_model_filename, CB_KART); + if(!obj) + { + fprintf(stderr, "Can't find kart model '%s'.\n",m_model_filename.c_str()); + return; + } + m_root = new ssgTransform(); + m_root->ref(); + m_root->addKid(obj); + ssgStripify(obj); + Vec3 min, max; + SSGHelp::MinMax(obj, &min, &max); + m_z_offset = min.getZ(); + m_kart_width = max.getX()-min.getX(); + m_kart_length = max.getY()-min.getY(); + m_kart_height = max.getZ()-min.getZ(); + sgVec3 move_kart_to_0_z; + sgSetVec3(move_kart_to_0_z, 0, 0, m_z_offset); + m_root->setTransform(move_kart_to_0_z); + + // Now set default some default parameters (if not defined) that + // depend on the size of the kart model (wheel position, center + // of gravity shift) + for(unsigned int i=0; i<4; i++) + { if(m_wheel_graphics_position[i].getX()==UNDEFINED) { m_wheel_graphics_position[i].setX( ( i==1||i==3) @@ -111,72 +111,72 @@ void KartModel::loadModels() : 0.5f*m_kart_width ); m_wheel_graphics_position[i].setY( (i<2) ? 0.5f*m_kart_length : -0.5f*m_kart_length); - m_wheel_graphics_position[i].setZ(0); - } - } - - // Load the wheel models. This can't be done early, since the default - // values for the graphical position must be defined, which in turn - // depend on the size of the model. - for(unsigned int i=0; i<4; i++) - { - m_wheel_model[i] = loader->load(m_wheel_filename[i], CB_KART); + m_wheel_graphics_position[i].setZ(0); + } + } + + // Load the wheel models. This can't be done early, since the default + // values for the graphical position must be defined, which in turn + // depend on the size of the model. + for(unsigned int i=0; i<4; i++) + { + m_wheel_model[i] = loader->load(m_wheel_filename[i], CB_KART); m_wheel_transform[i]= new ssgTransform(); #ifdef DEBUG m_wheel_transform[i]->setName("wheeltransform"); #endif - if(m_wheel_model[i]) - { + if(m_wheel_model[i]) + { m_wheel_transform[i]->addKid(m_wheel_model[i]); m_root->addKid(m_wheel_transform[i]); - - Vec3 min_wheel, max_wheel; - SSGHelp::MinMax(m_wheel_model[i], &min_wheel, &max_wheel); - m_wheel_graphics_radius[i] = (max_wheel.getZ()-min_wheel.getZ())*0.5f; + + Vec3 min_wheel, max_wheel; + SSGHelp::MinMax(m_wheel_model[i], &min_wheel, &max_wheel); + m_wheel_graphics_radius[i] = (max_wheel.getZ()-min_wheel.getZ())*0.5f; sgMat4 wheel_loc; sgVec3 hpr; sgZeroVec3(hpr); - sgMakeCoordMat4(wheel_loc, m_wheel_graphics_position[i].toFloat(), - hpr); - m_wheel_transform[i]->setTransform(wheel_loc); - } // if m_wheel_model[i] - } // for i<4 - if(!m_wheel_model[0]) - { - m_z_offset = m_kart_height*0.5f; - } - + sgMakeCoordMat4(wheel_loc, m_wheel_graphics_position[i].toFloat(), + hpr); + m_wheel_transform[i]->setTransform(wheel_loc); + } // if m_wheel_model[i] + } // for i<4 + if(!m_wheel_model[0]) + { + m_z_offset = m_kart_height*0.5f; + } + } // load -// ---------------------------------------------------------------------------- -/** Loads a single wheel node. Currently this is the name of the wheel model - * and the position of the wheel relative to the kart. - * \param wheel_name Name of the wheel, e.g. wheel-rear-left. - * \param index Index of this wheel in the global m_wheel* fields. - */ -void KartModel::loadWheelInfo(const lisp::Lisp* const lisp, - const std::string &wheel_name, int index) -{ - const lisp::Lisp* const wheel = lisp->getLisp(wheel_name); - if(!wheel) - { - // Only print the warning if a model filename is given. Otherwise the - // stk_config file is read (which has no model information). - if(m_model_filename!="") - { - fprintf(stderr, "Missing wheel information '%s' for model '%s'.\n", - wheel_name.c_str(), m_model_filename.c_str()); - fprintf(stderr, "This can be ignored, but the wheels will not rotate.\n"); - } - return; - } - wheel->get("model", m_wheel_filename[index] ); - wheel->get("position", m_wheel_graphics_position[index]); - wheel->get("physics-position", m_wheel_physics_position[index] ); - wheel->get("min-suspension", m_min_suspension[index] ); - wheel->get("max-suspension", m_max_suspension[index] ); -} // loadWheelInfo - +// ---------------------------------------------------------------------------- +/** Loads a single wheel node. Currently this is the name of the wheel model + * and the position of the wheel relative to the kart. + * \param wheel_name Name of the wheel, e.g. wheel-rear-left. + * \param index Index of this wheel in the global m_wheel* fields. + */ +void KartModel::loadWheelInfo(const lisp::Lisp* const lisp, + const std::string &wheel_name, int index) +{ + const lisp::Lisp* const wheel = lisp->getLisp(wheel_name); + if(!wheel) + { + // Only print the warning if a model filename is given. Otherwise the + // stk_config file is read (which has no model information). + if(m_model_filename!="") + { + fprintf(stderr, "Missing wheel information '%s' for model '%s'.\n", + wheel_name.c_str(), m_model_filename.c_str()); + fprintf(stderr, "This can be ignored, but the wheels will not rotate.\n"); + } + return; + } + wheel->get("model", m_wheel_filename[index] ); + wheel->get("position", m_wheel_graphics_position[index]); + wheel->get("physics-position", m_wheel_physics_position[index] ); + wheel->get("min-suspension", m_min_suspension[index] ); + wheel->get("max-suspension", m_max_suspension[index] ); +} // loadWheelInfo + // ---------------------------------------------------------------------------- /** Sets the default position for the physical wheels if they are not defined * in the data file. The default position is to have the wheels at the corner @@ -189,23 +189,23 @@ void KartModel::loadWheelInfo(const lisp::Lisp* const lisp, void KartModel::setDefaultPhysicsPosition(const Vec3 ¢er_shift, float wheel_radius) { - for(unsigned int i=0; i<4; i++) - { - if(m_wheel_physics_position[i].getX()==UNDEFINED) - { + for(unsigned int i=0; i<4; i++) + { + if(m_wheel_physics_position[i].getX()==UNDEFINED) + { m_wheel_physics_position[i].setX( ( i==1||i==3) ? -0.5f*m_kart_width - : 0.5f*m_kart_width - +center_shift.getX( )); + : 0.5f*m_kart_width + +center_shift.getX( )); m_wheel_physics_position[i].setY( (0.5f*m_kart_length-wheel_radius) - * ( (i<2) ? 1 : -1) - +center_shift.getY()); - // Set the connection point so that a maximum compressed wheel - // (susp. length=0) will still poke a little bit out under the - // kart - m_wheel_physics_position[i].setZ(wheel_radius-0.05f); - } // if physics position is not defined - } + * ( (i<2) ? 1 : -1) + +center_shift.getY()); + // Set the connection point so that a maximum compressed wheel + // (susp. length=0) will still poke a little bit out under the + // kart + m_wheel_physics_position[i].setZ(wheel_radius-0.05f); + } // if physics position is not defined + } } // setDefaultPhysicsPosition @@ -227,9 +227,17 @@ void KartModel::adjustWheels(float rotation, float steer, // the graphical wheel models don't look too wrong. for(unsigned int i=0; i<4; i++) { - clamped_suspension[i] = std::min(std::max(suspension[i], + m_min_suspension[i] = -1.3; // FIXME - why are these still not inited at this point? + m_max_suspension[i] = 1.3; + const float suspension_length = (m_max_suspension[i]-m_min_suspension[i])/2; + + clamped_suspension[i] = std::min(std::max(suspension[i]/2.5f, // somewhat arbitrary constant to reduce visible wheel movement m_min_suspension[i]), - m_max_suspension[i]); + m_max_suspension[i]); + float ratio = clamped_suspension[i] / suspension_length; + const int sign = ratio < 0 ? -1 : 1; + ratio = sign * fabsf(ratio*(2-ratio)); // expanded form of 1 - (1 - x)^2, i.e. making suspension display quadratic and not linear + clamped_suspension[i] = ratio*suspension_length; } // for i<4 sgMakeRotMat4( wheel_rot, 0, RAD_TO_DEGREE(-rotation), 0);