Пример #1
0
 public BasicWeapon(RectangularMask rectangularMask)
     : base(rectangularMask)
 {
     base.CollidingMode = CollidingMode.Inclusion;
     CollidingInclusionSet.Add(typeof(AI <MonkeyBoard>));
     CollidingInclusionSet.Add(typeof(BorderTile));
 }
Пример #2
0
        protected CollisionStatus IsCollidingInto(Position nextPosition, RectangularMask mask, Collidable <TBoard> otherCollidable)
        {
            // creates a dummy variable just to store the out value
            int dummyCollisionDistance;

            return(IsCollidingInto(new Position(), nextPosition, mask, otherCollidable, out dummyCollisionDistance));
        }
 public Rocket(RectangularMask rectangularMask = default(RectangularMask))
     : base(rectangularMask)
 {
     HomingSound   = new SoundPlayer(@"Resources/Sfx/weapon_homing.wav");
     AIKilledSound = new SoundPlayer(@"Resources/Sfx/explosion.wav");
     HomingSound.PlayLooping();
 }
Пример #4
0
 public Movable(RectangularMask rectangularMask = default(RectangularMask), IEnumerable <IMovement> movements = null, Position position = default(Position))
     : base(rectangularMask, position)
 {
     if (movements == null)
     {
         MovementList = new List <IMovement>();
     }
     else
     {
         MovementList = new List <IMovement>(movements);
     }
 }
Пример #5
0
 public Controllable(RectangularMask rectangularMask = default(RectangularMask), IEnumerable <IMovement> movements = null, Position position = default(Position))
     : base(rectangularMask, movements, position)
 {
 }
Пример #6
0
        protected CollisionStatus IsCollidingInto(Position previousPosition, Position nextPosition, RectangularMask mask, Collidable <TBoard> otherCollidable, out int collisionDistance)
        {
            // assume no collision first, and therefore collision distance is 0
            collisionDistance = 0;

            // check whether if the other collidable object is itself
            // if it is, ignore
            if (this == otherCollidable)
            {
                return(CollisionStatus.NoCollision);
            }

            // sometimes removal of board is done before this (because of the async nature of event handling)
            // if so, we ignore the collision
            if (Board == null)
            {
                return(CollisionStatus.NoCollision);
            }

            // we do checks according to the colliding mode
            // we also check whether the other collidable object's type
            // is found within the inclusion or exclusion set
            if (CollidingMode == Logic.CollidingMode.Exclusion && CollidingExclusionSet.Contains(otherCollidable.GetType()) ||
                otherCollidable.CollidingMode == Logic.CollidingMode.Exclusion && otherCollidable.CollidingExclusionSet.Contains(this.GetType()))
            {
                return(CollisionStatus.NoCollision);
            }

            else if (CollidingMode == Logic.CollidingMode.Inclusion ||
                     otherCollidable.CollidingMode == Logic.CollidingMode.Inclusion)
            {
                bool tmp = false;

                foreach (Type c in CollidingInclusionSet)
                {
                    if ((otherCollidable.GetType().IsSubclassOf(c) || this.GetType().IsSubclassOf(c)) ||
                        (otherCollidable.GetType().Equals(c)) || (this.GetType().Equals(c)))
                    {
                        tmp = true;
                        break;
                    }
                }

                if (!tmp)
                {
                    foreach (Type c in otherCollidable.CollidingInclusionSet)
                    {
                        if (otherCollidable.GetType().IsSubclassOf(c) || this.GetType().IsSubclassOf(c) ||
                            (otherCollidable.GetType().Equals(c)) || (this.GetType().Equals(c)))
                        {
                            tmp = true;
                            break;
                        }
                    }
                }

                if (!tmp)
                {
                    return(CollisionStatus.NoCollision);
                }
            }

            // IMPORTANT
            // check for mask collision here
            // refer to CollidableMaskCalculation.png for pictorial descriptions

            // note that a mask can at most take up a grid size
            // which is (FinenessLimit * 2) by (FinenessLimit * 2)

            // we will be converting all X and Y values into the absolute fineness values
            // for convenience in comparison

            // TODO:
            // should use subprocedure to calculate all these because most calculation parts
            // are the same

            // check for x-axis first
            RectangularMask otherMask               = otherCollidable.RectangularMask;
            int             otherMaskFinenessX      = otherCollidable.X * Board.FinenessLimit * 2 + otherCollidable.FinenessX;
            int             otherMaskLeftFinenessX  = otherMaskFinenessX + otherMask.LeftMargin;
            int             otherMaskRightFinenessX = otherMaskFinenessX + Board.FinenessLimit * 2 - 1 - otherMask.RightMargin;

            int maskFinenessX     = nextPosition.X * Board.FinenessLimit * 2 + nextPosition.FinenessX;
            int maskLeftFinenessX = maskFinenessX + mask.LeftMargin;
            // because the upper limit is exclusive unlike the lower limit, and since the fineness unit is discrete
            // there is a need to -1
            int maskRightFinenessX = maskFinenessX + Board.FinenessLimit * 2 - 1 - mask.RightMargin;

            // check collision now by comparing the mask
            // if x doesn't collide, that means it won't collide anyway, so return false
            if (!((maskLeftFinenessX <= otherMaskLeftFinenessX && otherMaskLeftFinenessX <= maskRightFinenessX) ||
                  (maskLeftFinenessX <= otherMaskRightFinenessX && otherMaskRightFinenessX <= maskRightFinenessX) ||
                  (otherMaskLeftFinenessX <= maskLeftFinenessX && maskLeftFinenessX <= otherMaskRightFinenessX) ||
                  (otherMaskLeftFinenessX <= maskRightFinenessX && maskRightFinenessX <= otherMaskRightFinenessX)))
            {
                return(CollisionStatus.NoCollision);
            }

            // now check for y-axis
            int otherMaskFinenessY       = otherCollidable.Y * Board.FinenessLimit * 2 + otherCollidable.FinenessY;
            int otherMaskTopFinenessY    = otherMaskFinenessY + otherMask.TopMargin;
            int otherMaskBottomFinenessY = otherMaskFinenessY + Board.FinenessLimit * 2 - 1 - otherMask.BottomMargin;

            int maskFinenessY       = nextPosition.Y * Board.FinenessLimit * 2 + nextPosition.FinenessY;
            int maskTopFinenessY    = maskFinenessY + mask.TopMargin;
            int maskBottomFinenessY = maskFinenessY + Board.FinenessLimit * 2 - 1 - mask.BottomMargin;

            // check collision now by comparing the mask
            // if y doesn't collide, return false
            if (!((maskTopFinenessY <= otherMaskTopFinenessY && otherMaskTopFinenessY <= maskBottomFinenessY) ||
                  (maskTopFinenessY <= otherMaskBottomFinenessY && otherMaskBottomFinenessY <= maskBottomFinenessY) ||
                  (otherMaskTopFinenessY <= maskTopFinenessY && maskTopFinenessY <= otherMaskBottomFinenessY) ||
                  (otherMaskTopFinenessY <= maskBottomFinenessY && maskBottomFinenessY <= otherMaskBottomFinenessY)))
            {
                return(CollisionStatus.NoCollision);
            }

            // this part onwards reveals where the collision is headed from
            CollisionStatus statusForOther;

            // first check for direction of collision for Y to solve a serious bug
            int previousFinenessY       = previousPosition.Y * Board.FinenessLimit * 2 + previousPosition.FinenessY;
            int previousTopFinenessY    = previousFinenessY + mask.TopMargin;
            int previousBottomFinenessY = previousFinenessY + Board.FinenessLimit * 2 - 1 - mask.BottomMargin;

            if (previousBottomFinenessY < otherMaskTopFinenessY)
            {
                collisionDistance = otherMaskTopFinenessY - previousBottomFinenessY - 1;
                statusForOther    = CollisionStatus.CollisionFromTop;
            }

            else if (previousTopFinenessY > otherMaskBottomFinenessY)
            {
                collisionDistance = previousTopFinenessY - otherMaskBottomFinenessY - 1;
                statusForOther    = CollisionStatus.CollisionFromBottom;
            }

            else
            {
                // next check for direction of collision for X first
                int previousFinenessX      = previousPosition.X * Board.FinenessLimit * 2 + previousPosition.FinenessX;
                int previousLeftFinenessX  = previousFinenessX + mask.LeftMargin;
                int previousRightFinenessX = previousFinenessX + Board.FinenessLimit * 2 - 1 - mask.RightMargin;

                if (previousRightFinenessX < otherMaskLeftFinenessX)
                {
                    // there is a need to minus 1 because without minusing, the two masks will exactly clip onto each other
                    // at the boundary. By minusing 1, the two masks will be exactly at side by side.
                    collisionDistance = otherMaskLeftFinenessX - previousRightFinenessX - 1;
                    statusForOther    = CollisionStatus.CollisionFromLeft;
                }

                else
                {
                    collisionDistance = previousLeftFinenessX - otherMaskRightFinenessX - 1;
                    statusForOther    = CollisionStatus.CollisionFromRight;
                }
            }

            return(statusForOther);
        }
Пример #7
0
 public Collidable(RectangularMask rectangularMask = default(RectangularMask), Position position = default(Position)) : base(position)
 {
     RectangularMask = rectangularMask;
 }
Пример #8
0
        protected CollisionStatus PerformCollidingInto(Position previousPosition, Position nextPosition, RectangularMask mask, Collidable <TBoard> otherCollidable, out int collisionDistance)
        {
            // instead of just checking for collision, this method will also trigger the collision after events
            CollisionStatus statusForOther  = IsCollidingInto(previousPosition, nextPosition, mask, otherCollidable, out collisionDistance);
            CollisionStatus statusForItself = CollisionStatus.NoCollision;

            switch (statusForOther)
            {
            case CollisionStatus.CollisionFromTop:
                statusForItself = CollisionStatus.CollisionFromBottom;
                break;

            case CollisionStatus.CollisionFromBottom:
                statusForItself = CollisionStatus.CollisionFromTop;
                break;

            case CollisionStatus.CollisionFromLeft:
                statusForItself = CollisionStatus.CollisionFromRight;
                break;

            case CollisionStatus.CollisionFromRight:
                statusForItself = CollisionStatus.CollisionFromLeft;
                break;
            }

            // calls class-specific behavioural methods. For instance, these methods will trigger removal of bananas from board when they collide with the monkey.
            if (statusForOther != CollisionStatus.NoCollision)
            {
                CollisionStatus newStatusForItself = BeforeCollision(otherCollidable, statusForItself);
                CollisionStatus newStatusForOther;

                if (newStatusForItself != CollisionStatus.NoCollision)
                {
                    newStatusForOther = otherCollidable.BeforeCollision(this, statusForOther);
                }
                else
                {
                    newStatusForOther = CollisionStatus.NoCollision;
                }

                CollisionAfter(otherCollidable, newStatusForItself);
                otherCollidable.CollisionAfter(this, newStatusForOther);

                return(newStatusForOther);
            }

            return(statusForOther);
        }
Пример #9
0
 public Tile(string tileIdentifier, RectangularMask rectangularMask) : base(rectangularMask)
 {
     // the identifier is meant for creating the correct TileUI
     TileIdentifier = tileIdentifier;
 }
Пример #10
0
 public NonKillableNonMovingAI(RectangularMask rectangularMask)
     : base(rectangularMask)
 {
 }
Пример #11
0
 public BasicMovingAI(RectangularMask rectangularMask)
     : base(rectangularMask)
 {
 }
Пример #12
0
 public NonMovingGravityAffectedAI(RectangularMask rectangularMask)
     : base(rectangularMask)
 {
 }
Пример #13
0
 public NonMovingAI(RectangularMask rectangularMask)
     : base(rectangularMask)
 {
     // set AI killed sound to be standard
     AIKilledSound = new SoundPlayer("Resources/Sfx/Enemy Killed.wav");
 }
Пример #14
0
 public Weapon(RectangularMask rectangularMask)
     : base(rectangularMask)
 {
 }
 public RocketRight(RectangularMask rectangularMask = default(RectangularMask))
     : base(rectangularMask)
 {
 }
Пример #16
0
 public AI(RectangularMask rectangularMask)
     : base(rectangularMask)
 {
 }