Exemple #1
0
    void Physics::detectCollisions (const std::vector<PhysicsObject*>& objects)
    {
        // Lets go through each collidable object checking if they collide.
        for (auto i = 0U; i < objects.size(); ++i)
        {
            // Cache the values for the first object.
            auto        first        = objects[i];
            const auto& check        = first->getCollider();
            const auto  checkLayer   = m_layers[check.getLayer()];

            auto checkBox           = check.getBox();
            checkBox.translate (first->getPosition().x, first->getPosition().y);

            for (auto j = i + 1; j < objects.size(); ++j)
            {
                // Cache the values for the second object.
                auto        second  = objects[j];
                const auto& against = second->getCollider();

                // Check if their layers collide.
                if ((checkLayer | (1 << against.getLayer())) > 0)
                {
                    // We must now check if the rectangles intersect.
                    auto againstBox = against.getBox();
                    againstBox.translate (second->getPosition().x, second->getPosition().y);

                    // Check if they intersect.
                    if (checkBox.intersects (againstBox))
                    {
                        // Determine the desired collision type.
                        if (check.isTrigger())
                        {
                            first->onTrigger (second);

                            if (against.isTrigger())
                            {
                                second->onTrigger (first);
                            }
                        }

                        // Collider on trigger.
                        else if (against.isTrigger())
                        {
                            second->onTrigger (first);
                        }

                        // Collider on collider.
                        else
                        {
                            first->onCollision (second);
                            second->onCollision (first);
                        }
                    }
                }
            }
        }
    }
void HelpScene::onUpdate()
{
	handleInput();
    update();
    onCollision();
   
}
Exemple #3
0
bool Ball::collisionHandler() {
    //IF they're a wall
    if (World::getInstance()->getGamePlayer(0)->getHealth() <= 0 && this->getY() + this->getRadius() > World::getInstance()->getWorldSize()*14/15) {
        this->setY(World::getInstance()->getWorldSize()*14/15 - this->getRadius());
        this->invertSpeedY();
        return true;
    }
    if (World::getInstance()->getGamePlayer(1)->getHealth() <= 0 && this->getX() + this->getRadius() > World::getInstance()->getWorldSize()*14/15) {
        this->setX(World::getInstance()->getWorldSize()*14/15 - this->getRadius());
        this->invertSpeedX();
        return true;
    }
    if (World::getInstance()->getGamePlayer(2)->getHealth() <= 0 && this->getY() - this->getRadius() < World::getInstance()->getWorldSize()/15) {
        this->setY(World::getInstance()->getWorldSize()/15 + this->getRadius());
        this->invertSpeedY();
        return true;
    }
    if (World::getInstance()->getGamePlayer(3)->getHealth() <= 0 && this->getX() - this->getRadius() < World::getInstance()->getWorldSize()/15) {
        this->setX(World::getInstance()->getWorldSize()/15 + this->getRadius());
        this->invertSpeedX();
        return true;
    }
    //if they block it
    foreach(Object *o, World::getInstance()->getObjects()) {
        double distance = o->getDistancetoPaddle(QPoint(this->getX(),this->getY()));
        if (distance != -1 && distance <= this->getRadius()) {
            onCollision(o);
            return true;
        }
    }
	void BlockOccurrence::onCollision(Collisionable* c, int collision_type)
	{
		/* Collisions vs Perso */
		Perso* perso = dynamic_cast<Perso*>(c);
		if(perso != NULL)
		{
			return onCollision(perso, collision_type);
		}
	}
Exemple #5
0
//判断是否发生碰撞
void ItemManager::testCollision(cocos2d::Node * render_node,IDisplayObject *pCollisionTarget)
{
    if (!mItemArray.empty()) {
        for (int i = 0; i < mItemArray.size(); i++) {
            auto pItem = mItemArray.at(i);
            pItem->onCollision(render_node,pCollisionTarget);
        }
    }
}
void Obstacle::onCollision(const float power)
{
	health-=power;

	if(health<=0)
	{
		onCollision();
		createBonus();
	}
}
	void ProjectileOccurrence::onCollision(Collisionable* c, int collision_type)
	{
		/* Collision vs BlockOccurrence */
		BlockOccurrence* block = dynamic_cast<BlockOccurrence*>(c);
		if(block != NULL)
		{
			return onCollision(block, collision_type);
		}

		/* Otherwise */
		_projectile->removeProjectileOccurrence(this);
	}
bool GameObject::checkCollision(const SDL_Rect& b, bool checkOnly){
    if(dead){
        return false;
    }

    int leftA, leftB;
    int rightA, rightB;
    int topA, topB;
    int bottomA, bottomB;

    leftA = posX;
    rightA = posX + width;
    topA = posY;
    bottomA = posY + height;

    leftB = b.x;
    rightB = b.x + b.w;
    topB = b.y;
    bottomB = b.y + b.h;

    if( bottomA <= topB ) {
        return false;
    }

    if( topA >= bottomB ){
        return false;
    }

    if( rightA <= leftB ){
        return false;
    }

    if( leftA >= rightB ) {
        return false;
    }

    if(!checkOnly){
        onCollision();
    }

    //If none of the sides from A are outside B
    return true;
}
Exemple #9
0
void GameObject::step(units::MS dt, const GroundPlane& ground_plane, std::vector<GameObject>& game_objects) {
   if (!should_move_) return;
   const glm::vec3 delta = velocity_ * static_cast<float>(dt);
   const glm::vec3 new_center = center_ + delta;
   if (Bounds(new_center.x - kRadius,
              new_center.x + kRadius).within(ground_plane.x_bounds()) &&
       Bounds(new_center.z - kRadius,
              new_center.z + kRadius).within(ground_plane.z_bounds())) {
      bool collided = false;
      for (auto& g : game_objects) {
         if (this != &g && BoundingSphere{new_center, kRadius}.collides(g.bounding_sphere())) {
            onCollision();
            g.onCollision();
            collided = true;
         }
      }
      if (!collided)
         center_ = new_center;
   } else {
      velocity_ = -velocity_;
      step(dt, ground_plane, game_objects);
   }
}
Exemple #10
0
void Projectile::processTick(const Move* move)
{
   Parent::processTick(move);

   mCurrTick++;
   if(mSourceObject && mCurrTick > SourceIdTimeoutTicks)
   {
      mSourceObject = 0;
      mSourceObjectId = 0;
   }

   // See if we can get out of here the easy way ...
   if (isServerObject() && mCurrTick >= mDataBlock->lifetime)
   {
      deleteObject();
      return;
   }
   else if (mHidden == true)
      return;

   // ... otherwise, we have to do some simulation work.
   RayInfo rInfo;
   Point3F oldPosition;
   Point3F newPosition;

   oldPosition = mCurrPosition;
   if(mDataBlock->isBallistic)
      mCurrVelocity.z -= 9.81 * mDataBlock->gravityMod * (F32(TickMs) / 1000.0f);

   newPosition = oldPosition + mCurrVelocity * (F32(TickMs) / 1000.0f);

   // disable the source objects collision reponse while we determine
   // if the projectile is capable of moving from the old position
   // to the new position, otherwise we'll hit ourself
   if (mSourceObject.isValid())
      mSourceObject->disableCollision();
   disableCollision();

   // Determine if the projectile is going to hit any object between the previous
   // position and the new position. This code is executed both on the server
   // and on the client (for prediction purposes). It is possible that the server
   // will have registered a collision while the client prediction has not. If this
   // happens the client will be corrected in the next packet update.

   // Raycast the abstract PhysicsWorld if a PhysicsPlugin exists.
   bool hit = false;

   if ( gPhysicsPlugin )
   {
      // TODO: hacked for single player... fix me!
      PhysicsWorld *world = gPhysicsPlugin->getWorld( "Server"/*isServerObject() ? "Server" : "Client"*/ );         
      if ( world )
         hit = world->castRay( oldPosition, newPosition, &rInfo, Point3F( newPosition - oldPosition) * mDataBlock->impactForce );            

   }
   else 
      hit = getContainer()->castRay(oldPosition, newPosition, csmDynamicCollisionMask | csmStaticCollisionMask, &rInfo);

   if ( hit )
   {
      // make sure the client knows to bounce
      if(isServerObject() && (rInfo.object->getType() & csmStaticCollisionMask) == 0)
         setMaskBits(BounceMask);

      // Next order of business: do we explode on this hit?
      if(mCurrTick > mDataBlock->armingDelay)
      {
         MatrixF xform(true);
         xform.setColumn(3, rInfo.point);
         setTransform(xform);
         mCurrPosition    = rInfo.point;
         mCurrVelocity    = Point3F(0, 0, 0);

         // Get the object type before the onCollision call, in case
         // the object is destroyed.
         U32 objectType = rInfo.object->getType();

         // re-enable the collision response on the source object since
         // we need to process the onCollision and explode calls
         if(mSourceObject)
            mSourceObject->enableCollision();

         // Ok, here is how this works:
         // onCollision is called to notify the server scripts that a collision has occurred, then
         // a call to explode is made to start the explosion process. The call to explode is made
         // twice, once on the server and once on the client.
         // The server process is responsible for two things:
         //    1) setting the ExplosionMask network bit to guarantee that the client calls explode
         //    2) initiate the explosion process on the server scripts
         // The client process is responsible for only one thing:
         //    1) drawing the appropriate explosion

         // It is possible that during the processTick the server may have decided that a hit
         // has occurred while the client prediction has decided that a hit has not occurred.
         // In this particular scenario the client will have failed to call onCollision and
         // explode during the processTick. However, the explode function will be called
         // during the next packet update, due to the ExplosionMask network bit being set.
         // onCollision will remain uncalled on the client however, therefore no client
         // specific code should be placed inside the function!
         onCollision(rInfo.point, rInfo.normal, rInfo.object);
         explode(rInfo.point, rInfo.normal, objectType );

         // break out of the collision check, since we've exploded
         // we don't want to mess with the position and velocity
      }
      else
      {
         if(mDataBlock->isBallistic)
         {
            // Otherwise, this represents a bounce.  First, reflect our velocity
            //  around the normal...
            Point3F bounceVel = mCurrVelocity - rInfo.normal * (mDot( mCurrVelocity, rInfo.normal ) * 2.0);;
            mCurrVelocity = bounceVel;

            // Add in surface friction...
            Point3F tangent = bounceVel - rInfo.normal * mDot(bounceVel, rInfo.normal);
            mCurrVelocity  -= tangent * mDataBlock->bounceFriction;

            // Now, take elasticity into account for modulating the speed of the grenade
            mCurrVelocity *= mDataBlock->bounceElasticity;

            // Set the new position to the impact and the bounce
            // will apply on the next frame.
            //F32 timeLeft = 1.0f - rInfo.t;
            newPosition = oldPosition = rInfo.point + rInfo.normal * 0.05f;
         }
      }
   }

   // re-enable the collision response on the source object now
   // that we are done processing the ballistic movement
   if (mSourceObject.isValid())
      mSourceObject->enableCollision();
   enableCollision();

   if(isClientObject())
   {
      emitParticles(mCurrPosition, newPosition, mCurrVelocity, TickMs);
      updateSound();
   }

   mCurrDeltaBase = newPosition;
   mCurrBackDelta = mCurrPosition - newPosition;
   mCurrPosition = newPosition;

   MatrixF xform(true);
   xform.setColumn(3, mCurrPosition);
   setTransform(xform);
}