예제 #1
0
bool TimeOfDay::onAdd()
{
   if ( !Parent::onAdd() )
      return false;
   
   // The server initializes to the specified starting values.
   // The client initializes itself to the server time from
   // unpackUpdate.
   if ( isServerObject() )
   {
      mTimeOfDay = mStartTimeOfDay;
   }

   // We don't use a bounds.
   setGlobalBounds();
   resetWorldBox();
   addToScene();

   // Lets receive ghost events so we can resolve
   // the sun object.
   if ( isClientObject() )
      NetConnection::smGhostAlwaysDone.notify( this, &TimeOfDay::_onGhostAlwaysDone );

   if ( isServerObject() )   
      Con::executef( this, "onAdd" );   

   return true;
}
예제 #2
0
파일: staticShape.cpp 프로젝트: Duion/GMK
//.logicking >>
void StaticShape::updatePhysics()
{
	SAFE_DELETE(mPhysicsRep);
	if ( PHYSICSMGR)
	{
		mShapeInstance->animate();

		// Get the interior collision geometry.
		ConcretePolyList polylist;
		if (buildPolyList(PLC_Collision, &polylist, getWorldBox(), getWorldSphere()))
		{
			polylist.triangulate();

			PhysicsCollision *colShape = PHYSICSMGR->createCollision();
			colShape->addTriangleMesh( polylist.mVertexList.address(), 
				polylist.mVertexList.size(),
				polylist.mIndexList.address(),
				polylist.mIndexList.size() / 3,
				MatrixF::Identity );

			PhysicsWorld *world = PHYSICSMGR->getWorld( isServerObject() ? "server" : "client" );
			mPhysicsRep = PHYSICSMGR->createBody();
			//.hack - set kinematic flag to prevent crash on deleting static shape in character sweep(deleting Doors)
			mPhysicsRep->init( colShape, 0, PhysicsBody::BF_KINEMATIC, this, world );
		}
		if (isServerObject())
			setMaskBits(PhysicsMask);
	}
}
예제 #3
0
void Trigger::potentialEnterObject(GameBase* enter)
{
   if( (!mDataBlock || mDataBlock->isClientSide) && isServerObject() )
      return;
   if( (mDataBlock && !mDataBlock->isClientSide) && isGhost() )
      return;

   for (U32 i = 0; i < mObjects.size(); i++) {
      if (mObjects[i] == enter)
         return;
   }

   if (testObject(enter) == true) {
      mObjects.push_back(enter);
      deleteNotify(enter);

      if(!mEnterCommand.isEmpty())
      {
         String command = String("%obj = ") + enter->getIdString() + ";" + mEnterCommand;
         Con::evaluate(command.c_str());
      }

      if( mDataBlock )
         mDataBlock->onEnterTrigger_callback( this, enter );
   }
}
예제 #4
0
void Etherform::addLaserTrailNode(const Point3F& pos)
{
	if( isServerObject() )
		return;

	for(S32 i = 0; i < NUM_ETHERFORM_LASERTRAILS; i++)
	{
		if( mLaserTrailList[i] == NULL )
		{
			// set up laserTrail...
			if( mDataBlock->laserTrailList[i] )
			{
				mLaserTrailList[i] = new MultiNodeLaserBeam();
				mLaserTrailList[i]->setPalette(this->getPalette());
				mLaserTrailList[i]->onNewDataBlock(mDataBlock->laserTrailList[i], false);
				if( !mLaserTrailList[i]->registerObject() )
				{
					Con::warnf( ConsoleLogEntry::General, "Could not register laserTrail %d for class: %s",i, mDataBlock->getName() );
					delete mLaserTrailList[i];
					mLaserTrailList[i] = NULL;
				}
				else
				{
					mLaserTrailList[i]->addNodes(pos);
					mLaserTrailList[i]->setRender(true);
					mLaserTrailList[i]->fade();
				}
			}
		}
		else
		{
			mLaserTrailList[i]->addNodes(pos);
		}
	}
}
void WayPoint::setHidden(bool hidden)
{
   // Skip ShapeBase::setHidden (only ever added to scene if in the editor)
   ShapeBase::Parent::setHidden( hidden );
   if(isServerObject())
      setMaskBits(UpdateHiddenMask);
}
예제 #6
0
bool GroundPlane::onAdd()
{
   if( !Parent::onAdd() )
      return false;

   if( isClientObject() )
      _updateMaterial();
      
   if( mSquareSize < sMIN_SQUARE_SIZE )
   {
      Con::errorf( "GroundPlane - squareSize below threshold; re-setting to %.02f", sMIN_SQUARE_SIZE );
      mSquareSize = sMIN_SQUARE_SIZE;
   }

   Parent::setScale( VectorF( 1.0f, 1.0f, 1.0f ) );
   Parent::setTransform( MatrixF::Identity );
   setGlobalBounds();
   resetWorldBox();

   addToScene();

   if ( PHYSICSMGR )
   {
      PhysicsCollision *colShape = PHYSICSMGR->createCollision();
      colShape->addPlane( PlaneF( Point3F::Zero, Point3F( 0, 0, 1 ) ) ); 

      PhysicsWorld *world = PHYSICSMGR->getWorld( isServerObject() ? "server" : "client" );
      mPhysicsRep = PHYSICSMGR->createBody();
      mPhysicsRep->init( colShape, 0, 0, this, world );
   }

   return true;
}
예제 #7
0
bool SFXEmitter::onAdd()
{
   if ( !Parent::onAdd() )
      return false;

   if ( isServerObject() )
   {
      // Validate the data we'll be passing across
      // the network to the client.
      mDescription.validate();
   }
   else
   {
      _update();

      // Do we need to start playback?
      if ( mPlayOnAdd && mSource )
         mSource->play();
   }

   // Setup the bounds.
   mObjBox.maxExtents = mObjScale;
   mObjBox.minExtents = mObjScale;
   mObjBox.minExtents.neg();
   resetWorldBox();
   addToScene();

   return true;
}
예제 #8
0
파일: item.cpp 프로젝트: Bloodknight/GMK
bool Item::onAdd()
{
   if (!Parent::onAdd() || !mDataBlock)
      return false;

   if (mStatic)
      mAtRest = true;
   mObjToWorld.getColumn(3,&delta.pos);

   // Setup the box for our convex object...
   mObjBox.getCenter(&mConvex.mCenter);
   mConvex.mSize.x = mObjBox.len_x() / 2.0;
   mConvex.mSize.y = mObjBox.len_y() / 2.0;
   mConvex.mSize.z = mObjBox.len_z() / 2.0;
   mWorkingQueryBox.minExtents.set(-1e9, -1e9, -1e9);
   mWorkingQueryBox.maxExtents.set(-1e9, -1e9, -1e9);

   if( !isHidden() && !mSubclassItemHandlesScene )
      addToScene();

   if (isServerObject())
   {
      if (!mSubclassItemHandlesScene)
         scriptOnAdd();
   }
   else if (mDataBlock->lightType != NoLight)
   {
      mDropTime = Sim::getCurrentTime();
   }

   _updatePhysics();

   return true;
}
예제 #9
0
bool PxSingleActor::onNewDataBlock( GameBaseData *dptr )
{
   // Since onNewDataBlock is actually called before onAdd for client objects
   // we need to initialize this here.
   mWorld = dynamic_cast<PxWorld*>( gPhysicsPlugin->getWorld( isServerObject() ? "server" : "client" ) );
   if ( !mWorld )
      return false;

   mDataBlock = dynamic_cast<PxSingleActorData*>(dptr);

   if ( !mDataBlock || !Parent::onNewDataBlock( dptr ) )
      return false;

   if ( isClientObject() )
   {
      if ( mShapeInstance )   
         SAFE_DELETE(mShapeInstance);      
      mShapeInstance = new TSShapeInstance( mDataBlock->shape, isClientObject() );
   }

   mObjBox = mDataBlock->shape->bounds;
   resetWorldBox();

   // Create the actor.
   _createActor(); 

   // Must be called by the leaf class (of GameBase) once everything is loaded.
   scriptOnNewDataBlock();

   return true;
}
예제 #10
0
   bool NavMesh::onAdd()
   {
      if(!Parent::onAdd())
         return false;

      mObjBox.set(Point3F(-1.0f, -1.0f, -1.0f),
         Point3F( 1.0f,  1.0f,  1.0f));
      resetWorldBox();

      addToScene();

      if(gEditingMission)
         mNetFlags.set(Ghostable);

      if(isServerObject())
      {
         mEventManager = new EventManager();
         if(!mEventManager->registerObject())
         {
            Con::errorf("Could not register EventManager for NavMesh %d!", getId());
            delete mEventManager;
         }
         else
         {
            mEventManager->setMessageQueue(mEventManager->getIdString());
            mEventManager->registerEvent("NavMeshLoad");
            mEventManager->registerEvent("NavMeshBuild");
         }
      }

      load();

      return true;
   }
예제 #11
0
void SoftBody::createPhysShape()
{
	Physics* physics = Physics::getPhysics(isServerObject());

	if (physics)
	{
		createUniqVertexList();

		PhysSoftInfo physDescr;
		
		physDescr.shapeType = PhysInfo::ST_SOFTMESH;
		physDescr.physPolyList = mPhysPolyList;
		physDescr.owner = this;
		physDescr.mass = mDataBlock->mass;
		physDescr.poseMatchKoef = mDataBlock->poseMatchKoef;
		for(U8 i=0;i<mDataBlock->attachedPointsNum;i++)
		{
			physDescr.attachPoints.push_back(mDataBlock->attachedPoints[i]);
		}

		mPhysShape = physics->createPhysShapeSoft(physDescr);

		mPhysShape->setTransform(mObjToWorld);
	}
}
예제 #12
0
void Sun::_initCorona()
{
   if ( isServerObject() )
      return;
      
   // Load texture...

   if ( mCoronaTextureName.isNotEmpty() )      
      mCoronaTexture.set( mCoronaTextureName, &GFXDefaultStaticDiffuseProfile, "CoronaTexture" );            

   // Make stateblock...

   if ( mCoronaSB.isNull() )
   {
      GFXStateBlockDesc desc;
      desc.setCullMode( GFXCullNone );
      desc.setAlphaTest( true, GFXCmpGreaterEqual, 1 );
      desc.setZReadWrite( false, false );
      desc.setBlend( true, GFXBlendSrcColor, GFXBlendOne );
      desc.samplersDefined = true;
      desc.samplers[0].textureColorOp = GFXTOPModulate;
      desc.samplers[0].colorArg1 = GFXTATexture;
      desc.samplers[0].colorArg2 = GFXTADiffuse;
      desc.samplers[0].alphaOp = GFXTOPModulate;
      desc.samplers[0].alphaArg1 = GFXTATexture;
      desc.samplers[0].alphaArg2 = GFXTADiffuse;

      mCoronaSB = GFX->createStateBlock(desc);

      desc.setFillModeWireframe();
      mCoronaWireframeSB = GFX->createStateBlock(desc);
   }
}
예제 #13
0
void TSStatic::processTick( const Move *move )
{
   AssertFatal( mPlayAmbient && mAmbientThread, "TSSTatic::adanceTime called with nothing to play." );

   if ( isServerObject() )
      mShapeInstance->advanceTime( TickSec, mAmbientThread );
}
예제 #14
0
void TSStatic::_updatePhysics()
{
   SAFE_DELETE( mPhysicsRep );

   if ( !PHYSICSMGR || mCollisionType == None )
      return;

   PhysicsCollision *colShape = NULL;
   if ( mCollisionType == Bounds )
   {
      MatrixF offset( true );
      offset.setPosition( mShape->center );
      colShape = PHYSICSMGR->createCollision();
      colShape->addBox( getObjBox().getExtents() * 0.5f * mObjScale, offset );         
   }
   else
      colShape = mShape->buildColShape( mCollisionType == VisibleMesh, getScale() );

   if ( colShape )
   {
      PhysicsWorld *world = PHYSICSMGR->getWorld( isServerObject() ? "server" : "client" );
      mPhysicsRep = PHYSICSMGR->createBody();
      mPhysicsRep->init( colShape, 0, 0, this, world );
      mPhysicsRep->setTransform( getTransform() );
   }
}
예제 #15
0
void DecalRoad::_onTerrainChanged( U32 type, TerrainBlock* tblock, const Point2I &min, const Point2I &max )
{
   // The client side object just stores the area that has changed
   // and waits for the (delayed) update event from the server
   // to actually perform the update.
   if ( isClientObject() && tblock->isClientObject() )
   {
      // Convert the min and max into world space.
      const F32 size = tblock->getSquareSize();
      const Point3F pos = tblock->getPosition();

      // TODO: I don't think this works right with tiling!
      Box3F dirty( F32( min.x * size ) + pos.x, F32( min.y * size ) + pos.y, -F32_MAX,
         F32( max.x * size ) + pos.x, F32( max.y * size ) + pos.y, F32_MAX );

      if ( !mTerrainUpdateRect.isValidBox() )
         mTerrainUpdateRect = dirty;
      else
         mTerrainUpdateRect.intersect( dirty );
   }
   // The server object only updates edges (doesn't clip to geometry)
   // and schedules an update to be sent to the client.
   else if ( isServerObject() && tblock->isServerObject() )
   {
      //_generateEdges();
      scheduleUpdate( TerrainChangedMask );
   }
}
예제 #16
0
//----------------------------------------------------------------------------
U32 FlyingVehicle::getCollisionMask()
{
   if (isServerObject())
      return sServerCollisionMask;
   else
      return sClientCollisionMask;
}
예제 #17
0
void Forest::applyRadialImpulse( const Point3F &origin, F32 radius, F32 magnitude )
{   
   if ( isServerObject() )
      return;   

   // Find all the trees in the radius
   // then get their accumulators and 
   // push our impulse into them.
   VectorF impulse( 0, 0, 0 );
   ForestWindAccumulator *accumulator = NULL;

   Vector<TreePlacementInfo> trees;
   getLocalWindTrees( origin, radius, &trees );
   for ( U32 i = 0; i < trees.size(); i++ )
   {
      const TreePlacementInfo &treeInfo = trees[i];
      accumulator = WINDMGR->getLocalWind( treeInfo.itemKey );
      if ( !accumulator )
         continue;

      impulse = treeInfo.pos - origin;
      impulse.normalize();
      impulse *= magnitude;

      accumulator->applyImpulse( impulse );
   }
}
예제 #18
0
//-----------------------------------------------------------------------------
// setRibbonDatablock
//-----------------------------------------------------------------------------
void RibbonNode::setRibbonDatablock(RibbonData* data)
{
   if ( isServerObject() )
   {
      setMaskBits( EmitterDBMask );
   }
   else
   {
      Ribbon* pRibbon = NULL;
      if ( data )
      {
         // Create emitter with new datablock
         pRibbon = new Ribbon;
         pRibbon->onNewDataBlock( data, false );
         if( pRibbon->registerObject() == false )
         {
            Con::warnf(ConsoleLogEntry::General, "Could not register base ribbon of class: %s", data->getName() ? data->getName() : data->getIdString() );
            delete pRibbon;
            return;
         }
      }

      // Replace emitter
      if ( mRibbon )
         mRibbon->deleteOnEnd();

      mRibbon = pRibbon;
   }

   mRibbonDatablock = data;
}
예제 #19
0
void AITurretShape::processTick(const Move* move)
{
   Parent::processTick(move);

   if (isServerObject() && mDamageState == Enabled)
   {
      _updateTurretState(TickSec);

      if (mScanForTargets)
      {
         // Perform a scan for targets
         _performScan();

         // If we found one, turn off the scan
         if (mTarget.isValid())
         {
            mScanForTargets = false;
         }
      }

      if (mTrackTarget)
      {
         _trackTarget(TickSec);

         // If the target is lost, no longer track it
         if (!mTarget.isValid())
         {
            mTrackTarget = false;
         }
      }
   }
}
예제 #20
0
void SceneObject::inspectPostApply()
{
   if( isServerObject() )
      setMaskBits( MountedMask );

   Parent::inspectPostApply();
}
예제 #21
0
void SceneObject::mountObject( SceneObject *obj, S32 node, const MatrixF &xfm )
{
   if ( obj->mMount.object == this )
   {
      // Already mounted to this
      // So update our node and xfm which may have changed.
      obj->mMount.node = node;
      obj->mMount.xfm = xfm;
   }
   else
   {
      if ( obj->mMount.object )
         obj->unmount();

      obj->mMount.object = this;
      obj->mMount.node = node;
      obj->mMount.link = mMount.list;
      obj->mMount.xfm = xfm;
      mMount.list = obj;

      // Assign PIDs to both objects
      if ( isServerObject() )
      {
         obj->getOrCreatePersistentId();
         if ( !obj->mMountPID )
         {
            obj->mMountPID = getOrCreatePersistentId();
            obj->mMountPID->incRefCount();
         }
      }

      obj->onMount( this, node );
   }
}
예제 #22
0
void SceneSpace::setTransform(const MatrixF & mat)
{  
   Parent::setTransform( mat );

   if( isServerObject() )
      setMaskBits( TransformMask );
}
예제 #23
0
void ParticleEmitterNode::setEmitterDataBlock(ParticleEmitterData* data)
{
   if ( isServerObject() )
   {
      setMaskBits( EmitterDBMask );
   }
   else
   {
      ParticleEmitter* pEmitter = NULL;
      if ( data )
      {
         // Create emitter with new datablock
         pEmitter = new ParticleEmitter;
         pEmitter->onNewDataBlock( data, false );
         if( pEmitter->registerObject() == false )
         {
            Con::warnf(ConsoleLogEntry::General, "Could not register base emitter for particle of class: %s", data->getName() ? data->getName() : data->getIdString() );
            delete pEmitter;
            return;
         }
      }

      // Replace emitter
      if ( mEmitter )
         mEmitter->deleteWhenEmpty();

      mEmitter = pEmitter;
   }

   mEmitterDatablock = data;
}
예제 #24
0
bool SceneObject::onAdd()
{
   if ( !Parent::onAdd() )
      return false;

   mIsScopeAlways = mNetFlags.test( ScopeAlways );

   mWorldToObj = mObjToWorld;
   mWorldToObj.affineInverse();
   resetWorldBox();

   setRenderTransform(mObjToWorld);

   resolveMountPID();

   smSceneObjectAdd.trigger(this);

   //.logicking guidebot >>
   if (isServerObject())
	   createWorldObject();
   //.logicking guidebot <<
   return true;

   return true;
}
예제 #25
0
bool AITurretShape::onAdd()
{
   if( !Parent::onAdd() )
      return false;

   // Add this object to the scene
   addToScene();

   _setScanBox();

   if (isServerObject())
      _initState();

   if (isServerObject())
      scriptOnAdd();

   return true;
}
예제 #26
0
void RigidBody::applyImpulse(const Point3F &pos, const Point3F &impulse)
{
	//Con::printf("RigidBody::applyImpulse: %p isServer :%d tick: %d",this,isServerObject(),isServerObject()? gServerProcessList.getTotalTicks():gClientProcessList.getTotalTicks());
	//Con::printf("applyImpulse");
	if(SimComponent().mEnabled && mPhysShape && (isServerObject() || !mHasServerPhysic))
	{
		mPhysShape->addForce(impulse,pos);
	}
}
예제 #27
0
void MissionArea::setArea(const RectI & area)
{
   // set it
   mArea = MissionArea::smMissionArea = area;

   // pass along..
   if(isServerObject())
      mNetFlags.set(UpdateMask);
}
예제 #28
0
bool AIPlayer::setPathDestination(const Point3F &pos)
{
   // Pathfinding only happens on the server.
   if(!isServerObject())
      return false;

   if(!getNavMesh())
      updateNavMesh();
   // If we can't find a mesh, just move regularly.
   if(!getNavMesh())
   {
      //setMoveDestination(pos);
      throwCallback("onPathFailed");
      return false;
   }

   // Create a new path.
   NavPath *path = new NavPath();

   path->mMesh = getNavMesh();
   path->mFrom = getPosition();
   path->mTo = pos;
   path->mFromSet = path->mToSet = true;
   path->mAlwaysRender = true;
   path->mLinkTypes = mLinkTypes;
   path->mXray = true;
   // Paths plan automatically upon being registered.
   if(!path->registerObject())
   {
      delete path;
      return false;
   }

   if(path->success())
   {
      // Clear any current path we might have.
      clearPath();
      clearCover();
      clearFollow();
      // Store new path.
      mPathData.path = path;
      mPathData.owned = true;
      // Skip node 0, which we are currently standing on.
      moveToNode(1);
      throwCallback("onPathSuccess");
      return true;
   }
   else
   {
      // Just move normally if we can't path.
      //setMoveDestination(pos, true);
      //return;
      throwCallback("onPathFailed");
      path->deleteObject();
      return false;
   }
}
예제 #29
0
void SpawnSphere::processTick( const Move *move )
{
   if ( isServerObject() && isMounted() )
   {
      MatrixF mat( true );
      mMount.object->getRenderMountTransform( 0.f, mMount.node, mMount.xfm, &mat );
      setTransform( mat );
   }
}
예제 #30
0
void TurretShape::updateMove(const Move* move)
{
   PROFILE_SCOPE( TurretShape_UpdateMove );

   if (!move)
      return;

   Point3F vec, pos;

   // Update orientation
   mTurretDelta.rotVec = mRot;

   VectorF rotVec(0, 0, 0);
   if (getAllowManualRotation())
   {
      if (mPitchAllowed)
      {
         rotVec.x = move->pitch * 2.0f;   // Assume that our -2PI to 2PI range was clamped to -PI to PI in script;
         if (mPitchRate > 0)
         {
            rotVec.x *= mPitchRate * TickSec;
         }
      }
      if (mHeadingAllowed)
      {
         rotVec.z = move->yaw * 2.0f;     // Assume that our -2PI to 2PI range was clamped to -PI to PI in script
         if (mHeadingRate > 0)
         {
            rotVec.z *= mHeadingRate * TickSec;
         }
      }
   }

   mRot.x += rotVec.x;
   mRot.z += rotVec.z;
   _applyLimits(mRot);

   if (isServerObject())
   {
      // As this ends up animating shape nodes, we have no sense of a transform and
      // render transform.  Therefore we treat this as the true transform and leave the
      // client shape node changes to interpolateTick() as the render transform.  Otherwise
      // on the client we'll have this node change from processTick() and then backstepping
      // and catching up to the true node change in interpolateTick(), which causes the
      // turret to stutter.
      _setRotation( mRot );
   }
   else
   {
      // If on the client, calc delta for backstepping
      mTurretDelta.rot = mRot;
      mTurretDelta.rotVec = mTurretDelta.rotVec - mTurretDelta.rot;
   }

   setMaskBits(TurretUpdateMask);
}