1) Added animation support for attachments, atm hardcoded for bomb only.

2) Instead of creating a new scene node every time something is attached
   to a kart, the same node will now be re-used (and is set as invisible
   otherwise).


git-svn-id: svn+ssh://svn.code.sf.net/p/supertuxkart/code/main/trunk@5173 178a84e3-b1eb-0310-8ba1-8eac791a3b58
This commit is contained in:
hikerstk
2010-04-11 22:48:01 +00:00
parent 89637add52
commit 91feb49998
9 changed files with 66 additions and 49 deletions

View File

@@ -211,6 +211,7 @@ void Camera::smoothMoveCamera(float dt, const Vec3 &wanted_position,
#undef DEBUG_CAMERA
#ifdef DEBUG_CAMERA
core::vector3df xyz = m_kart->getXYZ().toIrrVector();
xyz = core::vector3df(17.5, 0, 0);
m_camera->setTarget(xyz);
xyz.Y = xyz.Y+30;
m_camera->setPosition(xyz);

View File

@@ -36,7 +36,12 @@ Attachment::Attachment(Kart* kart)
m_kart = kart;
m_previous_owner = NULL;
m_node = NULL;
// If we attach a NULL mesh, we get a NULL scene node back. So we
// have to attach some kind of mesh, but make it invisible.
m_node = irr_driver->addAnimatedMesh(
attachment_manager->getMesh(ATTACH_BOMB));
m_node->setParent(m_kart->getNode());
m_node->setVisible(false);
} // Attachment
//-----------------------------------------------------------------------------
@@ -50,8 +55,12 @@ Attachment::~Attachment()
void Attachment::set(attachmentType type, float time, Kart *current_kart)
{
clear();
m_node = irr_driver->addMesh(attachment_manager->getMesh(type));
m_node->setParent(m_kart->getNode());
m_node->setMesh(attachment_manager->getMesh(type));
if(type==ATTACH_BOMB)
{
int num_frames = m_node->getEndFrame() - m_node->getStartFrame()+1;
m_node->setAnimationSpeed(num_frames / time);
}
m_type = type;
m_time_left = time;
m_previous_owner = current_kart;
@@ -63,7 +72,7 @@ void Attachment::set(attachmentType type, float time, Kart *current_kart)
m_initial_speed = m_kart->getSpeed();
if(m_initial_speed <= 1.5) m_initial_speed = 1.5; // if going very slowly or backwards, braking won't remove parachute
}
m_node->setVisible(true);
} // set
// -----------------------------------------------------------------------------
@@ -75,11 +84,7 @@ void Attachment::clear()
{
m_type=ATTACH_NOTHING;
m_time_left=0.0;
if(m_node)
{
irr_driver->removeNode(m_node);
m_node = NULL;
}
m_node->setVisible(false);
// Resets the weight of the kart if the previous attachment affected it
// (e.g. anvil). This must be done *after* setting m_type to
@@ -159,10 +164,9 @@ void Attachment::hitBanana(const Item &item, int new_attachment)
//** Moves a bomb from kart FROM to kart TO.
void Attachment::moveBombFromTo(Kart *from, Kart *to)
{
to->setAttachmentType(ATTACH_BOMB,
from->getAttachment()->getTimeLeft()+
stk_config->m_bomb_time_increase, from);
to->getAttachment()->set(ATTACH_BOMB,
from->getAttachment()->getTimeLeft()+
stk_config->m_bomb_time_increase, from);
from->getAttachment()->clear();
} // moveBombFromTo

View File

@@ -50,14 +50,14 @@ private:
float m_initial_speed; // for parachutes only
/** Scene node of the attachment, which will be attached to the kart's
* scene node. */
scene::ISceneNode *m_node;
scene::IAnimatedMeshSceneNode
*m_node;
Kart *m_previous_owner; // used by bombs so that it's not passed
// back to previous owner
RandomGenerator m_random;
public:
Attachment(Kart* _kart);
~Attachment();
Attachment(Kart* _kart);
~Attachment();
void set (attachmentType _type, float time, Kart *previous_kart=NULL);
void set (attachmentType _type) { set(_type, m_time_left); }
void clear ();

View File

@@ -69,7 +69,7 @@ void AttachmentManager::loadModels()
// FIXME LEAK: these models are not removed (unimportant, since they
// have to be in memory till the end of the game.
std::string full_path = file_manager->getModelFile(iat[i].file);
m_attachments[iat[i].attachment]=irr_driver->getMesh(full_path);
m_attachments[iat[i].attachment]=irr_driver->getAnimatedMesh(full_path);
} // for
} // reInit

View File

@@ -25,12 +25,12 @@
class AttachmentManager
{
private:
scene::IMesh *m_attachments[ATTACH_MAX];
scene::IAnimatedMesh *m_attachments[ATTACH_MAX];
public:
AttachmentManager() {};
/** Returns the mest for a certain attachment.
* \param type Type of the attachment needed. */
scene::IMesh *getMesh(attachmentType type) const {return m_attachments[type]; }
scene::IAnimatedMesh *getMesh(attachmentType type) const {return m_attachments[type]; }
void removeTextures ();
void loadModels ();
};

View File

@@ -22,7 +22,7 @@
//The AI debugging works best with just 1 AI kart, so set the number of karts
//to 2 in main.cpp with quickstart and run supertuxkart with the arg -N.
#undef AI_DEBUG
#define AI_DEBUG
#include "karts/controller/new_ai_controller.hpp"
@@ -837,13 +837,9 @@ float NewAIController::findNonCrashingAngle()
Vec3 final_left = q[3];
float very_right = -atan2(right.getX()-xyz.getX(),
right.getZ()-xyz.getZ())
;//- m_kart->getHeading();
right.getZ()-xyz.getZ());
float very_left = -atan2(left.getX()-xyz.getX(),
left.getZ()-xyz.getZ())
;//- m_kart->getHeading();
very_left = normalizeAngle(very_left);
very_right = normalizeAngle(very_right);
left.getZ()-xyz.getZ());
float dist = 0;
while(dist<40.0f)
@@ -858,8 +854,6 @@ float NewAIController::findNonCrashingAngle()
float angle_left = -atan2(left.getX()-xyz.getX(),
left.getZ()-xyz.getZ())
;//- m_kart->getHeading();
angle_left = normalizeAngle(angle_left);
angle_right = normalizeAngle(angle_right);
// Stop if the left and the right beam overlap.
if(angle_left<very_right ||

View File

@@ -59,7 +59,7 @@
Kart::Kart (const std::string& ident, int position,
const btTransform& init_transform)
: TerrainInfo(1),
Moveable(), m_powerup(this), m_attachment(this)
Moveable(), m_powerup(this)
#if defined(WIN32) && !defined(__CYGWIN__)
# pragma warning(1:4355)
@@ -390,7 +390,7 @@ void Kart::reset()
}
m_kart_properties->getKartModel()->setAnimation(KartModel::AF_DEFAULT);
m_view_blocked_by_plunger = 0.0;
m_attachment.clear();
m_attachment->clear();
m_powerup.reset();
m_race_position = 9;
@@ -519,7 +519,7 @@ void Kart::collectedItem(const Item &item, int add_info)
switch (type)
{
case Item::ITEM_BANANA:
m_attachment.hitBanana(item, add_info);
m_attachment->hitBanana(item, add_info);
break;
case Item::ITEM_NITRO_SMALL: m_collected_energy++; break;
@@ -715,9 +715,9 @@ void Kart::update(float dt)
// Let the kart raise 2m in the 2 seconds of the rescue
const float rescue_time = 2.0f;
const float rescue_height = 2.0f;
if(m_attachment.getType() != ATTACH_TINYTUX)
if(m_attachment->getType() != ATTACH_TINYTUX)
{
m_attachment.set( ATTACH_TINYTUX, rescue_time ) ;
m_attachment->set( ATTACH_TINYTUX, rescue_time ) ;
m_rescue_pitch = getHPR().getPitch();
m_rescue_roll = getHPR().getRoll();
race_state->itemCollected(getWorldKartId(), -1, -1);
@@ -731,7 +731,7 @@ void Kart::update(float dt)
setXYZRotation(getXYZ()+Vec3(0, rescue_height*dt/rescue_time, 0),
getRotation()*q_roll*q_pitch);
} // if rescue mode
m_attachment.update(dt);
m_attachment->update(dt);
//smoke drawing control point
if ( UserConfigParams::m_graphical_effects )
@@ -1091,7 +1091,7 @@ void Kart::updatePhysics(float dt)
m_bounce_back_time-=dt;
float engine_power = getActualWheelForce() + handleNitro(dt)
+ handleSlipstream(dt);
if(m_attachment.getType()==ATTACH_PARACHUTE) engine_power*=0.2f;
if(m_attachment->getType()==ATTACH_PARACHUTE) engine_power*=0.2f;
if(m_controls.m_accel) // accelerating
{ // For a short time after a collision disable the engine,
@@ -1335,6 +1335,11 @@ void Kart::endRescue()
void Kart::loadData()
{
m_kart_properties->getKartModel()->attachModel(&m_node);
// Attachment must be created after attachModel, since only then the
// scene node will exist (to which the attachment is added). But the
// attachment is needed in createPhysics (which gets the mass, which
// is dependent on the attachment).
m_attachment = new Attachment(this);
createPhysics();
// Attach Particle System

View File

@@ -89,7 +89,7 @@ protected: // Used by the AI atm
KartControl m_controls; // The kart controls (e.g. steering, fire, ...)
Powerup m_powerup;
float m_zipper_time_left; /**<Zipper time left. */
Attachment m_attachment;
Attachment *m_attachment;
/** Easier access for player_kart. */
Camera *m_camera;
private:
@@ -218,7 +218,7 @@ public:
/** Sets the attachment and time it stays attached. */
void attach(attachmentType attachment_, float time)
{
m_attachment.set(attachment_, time);
m_attachment->set(attachment_, time);
}
// ------------------------------------------------------------------------
/** Sets a new powerup. */
@@ -236,47 +236,60 @@ public:
} // setPosition
// ------------------------------------------------------------------------
/** Returns the current attachment. */
Attachment *getAttachment()
{
return &m_attachment;
return m_attachment;
} // getAttachment
// ------------------------------------------------------------------------
void setAttachmentType(attachmentType t, float time_left=0.0f, Kart*k=NULL)
{
m_attachment.set(t, time_left, k);
}
// ------------------------------------------------------------------------
/** Returns the camera of this kart (or NULL if no camera is attached
* to this kart). */
Camera* getCamera () {return m_camera;}
// ------------------------------------------------------------------------
/** Returns the camera of this kart (or NULL if no camera is attached
* to this kart) - const version. */
const Camera* getCamera () const {return m_camera;}
// ------------------------------------------------------------------------
/** Sets the camera for this kart. */
void setCamera(Camera *camera) {m_camera=camera; }
// ------------------------------------------------------------------------
/** Returns the current powerup. */
const Powerup *getPowerup () const { return &m_powerup; }
// ------------------------------------------------------------------------
/** Returns the current powerup. */
Powerup *getPowerup () { return &m_powerup; }
// ------------------------------------------------------------------------
/** Returns the number of powerups. */
int getNumPowerup () const { return m_powerup.getNum(); }
// ------------------------------------------------------------------------
/** Returns the time left for a zipper. */
float getZipperTimeLeft () const { return m_zipper_time_left; }
// ------------------------------------------------------------------------
/** Returns the remaining collected energy. */
float getEnergy () const { return m_collected_energy; }
// ------------------------------------------------------------------------
/** Returns the current position of this kart in the race. */
int getPosition () const { return m_race_position; }
// ------------------------------------------------------------------------
/** Returns the initial position of this kart. */
int getInitialPosition () const { return m_initial_position; }
// ------------------------------------------------------------------------
/** Returns the finished time for a kart. */
float getFinishTime () const { return m_finish_time; }
// ------------------------------------------------------------------------
/** Returns true if this kart has finished the race. */
bool hasFinishedRace () const { return m_finished_race; }
// ------------------------------------------------------------------------
void endRescue ();
// ------------------------------------------------------------------------
/** Returns true if the kart has a plunger attached to its face. */
bool hasViewBlockedByPlunger() const
{ return m_view_blocked_by_plunger > 0; }
void blockViewWithPlunger() { m_view_blocked_by_plunger = 10; }
{ return m_view_blocked_by_plunger > 0; }
// ------------------------------------------------------------------------
/** Sets that the view is blocked by a plunger. */
void blockViewWithPlunger() { m_view_blocked_by_plunger = 10;}
/** Returns a bullet transform object located at the kart's position
and oriented in the direction the kart is going. Can be useful
@@ -292,7 +305,7 @@ public:
float getMass () const
{
return m_kart_properties->getMass()
+ m_attachment.weightAdjust();
+ m_attachment->weightAdjust();
}
float getMaxPower () const {return m_kart_properties->getMaxPower();}
float getTimeFullSteer () const {return m_kart_properties->getTimeFullSteer();}

View File

@@ -50,7 +50,7 @@ Moveable::~Moveable()
*/
void Moveable::setNode(scene::ISceneNode *n)
{
m_node = n;
m_node = n;
} // setNode
//-----------------------------------------------------------------------------