//////////////////////////////////////////////////////////////////////////////// // Scorched3D (c) 2000-2003 // // This file is part of Scorched3D. // // Scorched3D is free software; you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by // the Free Software Foundation; either version 2 of the License, or // (at your option) any later version. // // Scorched3D is distributed in the hope that it will be useful, // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the // GNU General Public License for more details. // // You should have received a copy of the GNU General Public License // along with Scorched3D; if not, write to the Free Software // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA //////////////////////////////////////////////////////////////////////////////// #include #include #include #include #include #include #include #include <3dsparse/ModelStore.h> #include <3dsparse/ModelRenderer.h> #include #include REGISTER_ACTION_SOURCE(ShotBounce); ShotBounce::ShotBounce() : collisionInfo_(CollisionIdBounce), totalTime_(0.0f), vPoint_(0), model_(0), data_(0) { } ShotBounce::ShotBounce(Vector &startPosition, Vector &velocity, WeaponRoller *weapon, unsigned int playerId, unsigned int data) : collisionInfo_(CollisionIdBounce), startPosition_(startPosition), velocity_(velocity), weapon_(weapon), playerId_(playerId), totalTime_(0.0f), vPoint_(0), model_(0), data_(data) { } void ShotBounce::init() { setPhysics(startPosition_, velocity_, 1.0f, 5.0f, weapon_->getWindFactor()); collisionInfo_.data = this; collisionInfo_.collisionOnSurface = true; physicsObject_.setData(&collisionInfo_); Vector lookatPos; vPoint_ = context_->viewPoints->getNewViewPoint(playerId_); context_->viewPoints->getValues(lookatPos, lookFrom_); } ShotBounce::~ShotBounce() { delete model_; if (vPoint_) context_->viewPoints->releaseViewPoint(vPoint_); } void ShotBounce::collision(Vector &position) { if (!collision_) { doCollision(); } PhysicsParticleMeta::collision(position); } void ShotBounce::simulate(float frameTime, bool &remove) { totalTime_ += frameTime; if (totalTime_ > weapon_->getTime()) { if (context_->serverMode) doCollision(); remove = true; } PhysicsParticleMeta::simulate(frameTime, remove); } void ShotBounce::draw() { if (!context_->serverMode) { static double rotMatrix[16]; static dReal quat[4]; float *fquat = getRotationQuat(); for (int i=0; i<4; i++) quat[i] = (dReal) fquat[i]; // And I thought this would be easy!! dMatrix3 matrix; dQtoR(quat, matrix); rotMatrix[0] = matrix[0]; rotMatrix[1] = matrix[4]; rotMatrix[2] = matrix[8]; rotMatrix[4] = matrix[1]; rotMatrix[5] = matrix[5]; rotMatrix[6] = matrix[9]; rotMatrix[8] = matrix[2]; rotMatrix[9] = matrix[6]; rotMatrix[10] = matrix[10]; rotMatrix[3] = rotMatrix[7] = rotMatrix[11] = 0.0; rotMatrix[15] = 1.0; rotMatrix[12] = rotMatrix[13] = rotMatrix[14] = 0.0; if (!model_) { ModelID &id = ((WeaponRoller *) weapon_)->getRollerModelID(); bool useTexture = (strcmp(id.getSkinName(), "none") != 0); model_ = new ModelRenderer( ModelStore::instance()->loadModel(id)); } if (vPoint_) { vPoint_->setPosition(getCurrentPosition()); vPoint_->setLookFrom(lookFrom_); } GLState state(GLState::TEXTURE_OFF); glPushMatrix(); glTranslatef( getCurrentPosition()[0], getCurrentPosition()[1], getCurrentPosition()[2]); glMultMatrixd(rotMatrix); glScalef(0.08f, 0.08f, 0.08f); model_->draw(); glPopMatrix(); } } void ShotBounce::doCollision() { WeaponRoller *proj = (WeaponRoller *) weapon_; proj->getCollisionAction()->fireWeapon( *context_, playerId_, getCurrentPosition(), getCurrentVelocity(), data_); } bool ShotBounce::writeAction(NetBuffer &buffer) { buffer.addToBuffer(playerId_); buffer.addToBuffer(data_); buffer.addToBuffer(startPosition_); buffer.addToBuffer(velocity_); context_->accessoryStore->writeWeapon(buffer, weapon_); return true; } bool ShotBounce::readAction(NetBufferReader &reader) { if (!reader.getFromBuffer(playerId_)) return false; if (!reader.getFromBuffer(data_)) return false; if (!reader.getFromBuffer(startPosition_)) return false; if (!reader.getFromBuffer(velocity_)) return false; weapon_ = (WeaponRoller *) context_->accessoryStore->readWeapon(reader); if (!weapon_) return false; // Point the action camera at this event const float ShowTime = 5.0f; ActionMeta *pos = new CameraPositionAction( startPosition_, ShowTime, 5); context_->actionController->getBuffer().clientAdd(-4.0f, pos); return true; }