⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 shapebase.cc

📁 五行MMORPG引擎系统V1.0
💻 CC
📖 第 1 页 / 共 5 页
字号:
         Thread& st = mScriptThread[i];
         if (st.sequence != -1) {
            // TG: Need to see about supressing non-cyclic sounds
            // if the sequences were actived before the object was
            // ghosted.
            // TG: Cyclic animations need to have a random pos if
            // they were started before the object was ghosted.

            // If there was something running on the old shape, the thread
            // needs to be reset. Otherwise we assume that it's been
            // initialized either by the constructor or from the server.
            bool reset = st.thread != 0;
            st.thread = 0;
            setThreadSequence(i,st.sequence,reset);
         }
      }

      // get rid of current shadow...we'll generate new one when needed
      delete mShadow;
      mShadow = NULL;

      if (mDataBlock->damageSequence != -1) {
         mDamageThread = mShapeInstance->addThread();
         mShapeInstance->setSequence(mDamageThread,
                                     mDataBlock->damageSequence,0);
      }
      if (mDataBlock->hulkSequence != -1) {
         mHulkThread = mShapeInstance->addThread();
         mShapeInstance->setSequence(mHulkThread,
                                     mDataBlock->hulkSequence,0);
      }
   }

   if (isGhost() && mSkinNameHandle.isValidString() && mShapeInstance) {

      mShapeInstance->reSkin(mSkinNameHandle);

      mSkinHash = _StringTable::hashString(mSkinNameHandle.getString());

   }


   //Skin modifier
   if (isGhost() && mShapeInstance)
   {
      mShapeInstance->updateModifiers();
   }


   //
   mEnergy = 0;
   mDamage = 0;
   mDamageState = Enabled;
   mRepairReserve = 0;
   updateMass();
   updateDamageLevel();
   updateDamageState();

   mDrag = mDataBlock->drag;
   mCameraFov = mDataBlock->cameraDefaultFov;
   return true;
}

void ShapeBase::onDeleteNotify(SimObject* obj)
{
   if (obj == getProcessAfter())
      clearProcessAfter();
   Parent::onDeleteNotify(obj);
   if (obj == mMount.object)
      unmount();
}

void ShapeBase::onImpact(SceneObject* obj, VectorF vec)
{
#ifndef TGE_RPGCLIENT2 /// TGE_RPGIsClientObject
   if (!isGhost()) 
#endif
	{
      char buff1[256];
      char buff2[32];

      dSprintf(buff1,sizeof(buff1),"%g %g %g",vec.x, vec.y, vec.z);
      dSprintf(buff2,sizeof(buff2),"%g",vec.len());
      Con::executef(mDataBlock,5,"onImpact",scriptThis(), obj->getIdString(), buff1, buff2);
   }
}

void ShapeBase::onImpact(VectorF vec)
{
#ifndef TGE_RPGCLIENT2 /// TGE_RPGIsClientObject
   if (!isGhost()) 
#endif
	{
      char buff1[256];
      char buff2[32];

      dSprintf(buff1,sizeof(buff1),"%g %g %g",vec.x, vec.y, vec.z);
      dSprintf(buff2,sizeof(buff2),"%g",vec.len());
      Con::executef(mDataBlock,5,"onImpact",scriptThis(), "0", buff1, buff2);
   }
}


//----------------------------------------------------------------------------

void ShapeBase::processTick(const Move* move)
{

#ifdef TGE_RPG /// TGE_Move
	/// 相机管理
	//if(move)
	//{
 //     m_rotCamera.x += move->pitch;
	//	m_rotCamera.x  = mClampF(m_rotCamera.x ,ms_fCameraMinPitch*M_PI_DIV180,ms_fCameraMaxPitch*M_PI_DIV180);
 //     m_rotCamera.z += move->yaw;
 //     m_rotCamera.z  = mFmod(m_rotCamera.z, M_2PI_F);
	//	m_fCameraDist += move->z;
	//	m_fCameraDist  = mClampF(move->z, mDataBlock->cameraMinDist, mDataBlock->cameraMaxDist);
	//}
#endif

   // Energy management
   if (mDamageState == Enabled && mDataBlock->inheritEnergyFromMount == false) {
      F32 store = mEnergy;
      mEnergy += mRechargeRate;
      if (mEnergy > mDataBlock->maxEnergy)
         mEnergy = mDataBlock->maxEnergy;
      else
         if (mEnergy < 0)
            mEnergy = 0;

      // Virtual setEnergyLevel is used here by some derived classes to
      // decide whether they really want to set the energy mask bit.
      if (mEnergy != store)
         setEnergyLevel(mEnergy);
   }

   // Repair management
   if (mDataBlock->isInvincible == false)
   {
      F32 store = mDamage;
      mDamage -= mRepairRate;
      mDamage = mClampF(mDamage, 0.f, mDataBlock->maxDamage);

      if (mRepairReserve > mDamage)
         mRepairReserve = mDamage;
      if (mRepairReserve > 0.0)
      {
         F32 rate = getMin(mDataBlock->repairRate, mRepairReserve);
         mDamage -= rate;
         mRepairReserve -= rate;
      }

      if (store != mDamage)
      {
         updateDamageLevel();
         if (isServerObject()) {
            char delta[100];
            dSprintf(delta,sizeof(delta),"%g",mDamage - store);
            setMaskBits(DamageMask);
            Con::executef(mDataBlock,3,"onDamage",scriptThis(),delta);
         }
      }
   }

   if (isServerObject()) {
      // Server only...
      advanceThreads(TickSec);
      updateServerAudio();

      // update wet state
      setImageWetState(0, mWaterCoverage > 0.4); // more than 40 percent covered

      if(mFading)
      {
         F32 dt = TickMs / 1000.0;
         F32 newFadeET = mFadeElapsedTime + dt;
         if(mFadeElapsedTime < mFadeDelay && newFadeET >= mFadeDelay)
            setMaskBits(CloakMask);
         mFadeElapsedTime = newFadeET;
         if(mFadeElapsedTime > mFadeTime + mFadeDelay)
         {
            mFadeVal = F32(!mFadeOut);
            mFading = false;
         }
      }
   }

   // Advance images
   for (int i = 0; i < MaxMountedImages; i++)
   {
      if (mMountedImageList[i].dataBlock != NULL)
         updateImageState(i, TickSec);
   }

   // Call script on trigger state changes
   if (move && mDataBlock && isServerObject()) {
      for (S32 i = 0; i < MaxTriggerKeys; i++) {
         if (move->trigger[i] != mTrigger[i]) {
            mTrigger[i] = move->trigger[i];
            char buf1[20],buf2[20];
            dSprintf(buf1,sizeof(buf1),"%d",i);
            dSprintf(buf2,sizeof(buf2),"%d",(move->trigger[i]?1:0));
            Con::executef(mDataBlock,4,"onTrigger",scriptThis(),buf1,buf2);
         }
      }
   }

   // Update the damage flash and the whiteout
   //
   if (mDamageFlash > 0.0)
   {
      mDamageFlash -= sDamageFlashDec;
      if (mDamageFlash <= 0.0)
         mDamageFlash = 0.0;
   }
   if (mWhiteOut > 0.0)
   {
      mWhiteOut -= sWhiteoutDec;
      if (mWhiteOut <= 0.0)
         mWhiteOut = 0.0;
   }
}

void ShapeBase::advanceTime(F32 dt)
{
   // On the client, the shape threads and images are
   // advanced at framerate.
   advanceThreads(dt);
   updateAudioPos();
   for (int i = 0; i < MaxMountedImages; i++)
      if (mMountedImageList[i].dataBlock)
         updateImageAnimation(i,dt);

   // Cloaking takes 0.5 seconds
   if (mCloaked && mCloakLevel != 1.0) {
      mCloakLevel += dt * 2;
      if (mCloakLevel >= 1.0)
         mCloakLevel = 1.0;
   } else if (!mCloaked && mCloakLevel != 0.0) {
      mCloakLevel -= dt * 2;
      if (mCloakLevel <= 0.0)
         mCloakLevel = 0.0;
   }
   if(mInvincibleOn)
      updateInvincibleEffect(dt);

   if(mFading)
   {
      mFadeElapsedTime += dt;
      if(mFadeElapsedTime > mFadeTime)
      {
         mFadeVal = F32(!mFadeOut);
         mFading = false;
      }
      else
      {
         mFadeVal = mFadeElapsedTime / mFadeTime;
         if(mFadeOut)
            mFadeVal = 1 - mFadeVal;
      }
   }
}


//----------------------------------------------------------------------------

//void ShapeBase::setControllingClient(GameConnection* client)
//{
//   mControllingClient = client;
//
//   // piggybacks on the cloak update
//   setMaskBits(CloakMask);
//}

void ShapeBase::setControllingObject(ShapeBase* obj)
{
   if (obj) {
      setProcessTick(false);
      // Even though we don't processTick, we still need to
      // process after the controller in case anyone is mounted
      // on this object.
      processAfter(obj);
   }
   else {
      setProcessTick(true);
      clearProcessAfter();
      // Catch the case of the controlling object actually
      // mounted on this object.
      if (mControllingObject->mMount.object == this)
         mControllingObject->processAfter(this);
   }
   mControllingObject = obj;
}

ShapeBase* ShapeBase::getControlObject()
{
   return 0;
}

void ShapeBase::setControlObject(ShapeBase*)
{
}

bool ShapeBase::isFirstPerson()
{
   // Always first person as far as the server is concerned.
   if (!isGhost())
      return true;

   if (GameConnection* con = getControllingClient())
      return con->getControlObject() == this && con->isFirstPerson();
   return false;
}

// Camera: (in degrees) ------------------------------------------------------
F32 ShapeBase::getCameraFov()
{
   return(mCameraFov);
}

F32 ShapeBase::getDefaultCameraFov()
{
   return(mDataBlock->cameraDefaultFov);
}

bool ShapeBase::isValidCameraFov(F32 fov)
{
   return((fov >= mDataBlock->cameraMinFov) && (fov <= mDataBlock->cameraMaxFov));
}

void ShapeBase::setCameraFov(F32 fov)
{
   mCameraFov = mClampF(fov, mDataBlock->cameraMinFov, mDataBlock->cameraMaxFov);
}

//----------------------------------------------------------------------------
static void scopeCallback(SceneObject* obj, void *conPtr)
{
   NetConnection * ptr = reinterpret_cast<NetConnection*>(conPtr);
   if (obj->isScopeable())
      ptr->objectInScope(obj);
}

void ShapeBase::onCameraScopeQuery(NetConnection *cr, CameraScopeQuery * query)
{
   // update the camera query
   query->camera = this;

   // bool grabEye = true;
   if(GameConnection * con = dynamic_cast<GameConnection*>(cr))
   {
      // get the fov from the connection (in deg)
      F32 fov;
      if (con->getControlCameraFov(&fov))
      {
         query->fov = mDegToRad(fov/2);
         query->sinFov = mSin(query->fov);
         query->cosFov = mCos(query->fov);
      }
   }

   // failed to query the camera info?
   // if(grabEye)    LH - always use eye as good enough, avoid camera animate
   {
      MatrixF eyeTransform;
      getEyeTransform(&eyeTransform);
      eyeTransform.getColumn(3, &query->pos);
      eyeTransform.getColumn(1, &query->orientation);
   }

   // grab the visible distance from the sky
   Sky * sky = gServerSceneGraph->getCurrentSky();
   if(sky)
      query->visibleDistance = sky->getVisibleDistance();
   else
      query->visibleDistance = 1000.f;

   // First, we are certainly in scope, and whatever we're riding is too...
   cr->objectInScope(this);
   if (isMounted())
      cr->objectInScope(mMount.object);

   if (mSceneManager == NULL)
   {
      // Scope everything...
      gServerContainer.findObjects(0xFFFFFFFF,scopeCallback,cr);
      return;
   }

   // update the scenemanager
   mSceneManager->scopeScene(query->pos, query->visibleDistance, cr);

   // let the (game)connection do some scoping of its own (commandermap...)
   cr->doneScopingScene();
}


//----------------------------------------------------------------------------
F32 ShapeBase::getEnergyLevel()
{
   if (mDataBlock->inheritEnergyFromMount == false)
      return mEnergy;
   else if (isMounted()) {
      return getObjectMount()->getEnergyLevel();
   } else {
      return 0.0f;
   }
}

F32 ShapeBase::getEnergyValue()
{
   if (mDataBlock->inheritEnergyFromMount == false) {
      F32 maxEnergy = mDataBlock->maxEnergy;
      if ( maxEnergy > 0.f )
         return (mEnergy / mDataBlock->maxEnergy);
   } else if (isMounted()) {
      F32 maxEnergy = getObjectMount()->mDataBlock->maxEnergy;
      if ( maxEnergy > 0.f )
         return (getObjectMount()->getEnergyLevel() / maxEnergy);
   }
   return 0.0f;
}

void ShapeBase::setEnergyLevel(F32 energy)
{
   if (mDataBlock->inheritEnergyFromMount == false) {
      if (mDamageState == Enabled) {
         mEnergy = (energy > mDataBlock->maxEnergy)?
            mDataBlock->maxEnergy: (energy < 0)? 0: energy;
      }
   } else {
      // Pass the set onto whatever we're mounted to...
      if (isMounted())
         getObjectMount()->setEnergyLevel(energy);
   }
}

void ShapeBase::setDamageLevel(F32 damage)
{
   if (!mDataBlock->isInvincible) {
      F32 store = mDamage;
      mDamage = mClampF(damage, 0.f, mDataBlock->maxDamage);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -