/**
     * // Find out our Y-position on the slope we're currently using
     * float CalculateAltitude(float progress)
     * {
     *      return ground.self.position.y + ground.verticalOffset * ground.self.localScale.y + ground.yScale * ground.slopeCurve.Evaluate(progress) * ground.self.localScale.y;
     * }
     *
     * // Called at each grounded movement
     * bool UpdateSlope()
     * {
     *      float progress = (self.position.x - ground.xMin) / (ground.xMax - ground.xMin);
     *      progress = Mathf.Clamp01(progress);
     *      float yNeeded = CalculateAltitude(progress);
     *
     *      // Manually set our Y-coordinate if we're grounded
     *      if(bottom < yNeeded)
     *      {
     *              self.position = new Vector3(self.position.x, yNeeded + bottomDelta, self.position.z);
     *
     *              if(!collisionFlags.down)
     *              {
     *                      if (onCollisionEnter != null) onCollisionEnter(new RaycastHitPlus());
     *                      if (onVerticalCollisionEnter != null) onVerticalCollisionEnter(new RaycastHitPlus());
     *              }
     *
     *              collisionFlags.down = true;
     *      }
     *      if(self.position.y == yNeeded + bottomDelta) collisionFlags.down = true;
     *
     *      return bottom <= yNeeded;
     * }
     *
     * // Get the angle of the current slope based on the altitude "just behind us" and "just in front of us".
     * float FindAngle()
     * {
     *      if(!ground || ignoreSlopeZones) return 0;
     *
     *      float result = 0;
     *
     *      float prevProgress = (self.position.x - stepSize - ground.xMin) / (ground.xMax - ground.xMin);
     *      prevProgress = Mathf.Clamp01(prevProgress);
     *      float yPrev = CalculateAltitude(prevProgress);
     *
     *      float nextProgress = (self.position.x + stepSize - ground.xMin) / (ground.xMax - ground.xMin);
     *      nextProgress = Mathf.Clamp01(nextProgress);
     *      float yNext = CalculateAltitude(nextProgress);
     *
     *      Vector2 before = new Vector2(self.position.x - stepSize, yPrev);
     *      Vector2 after = new Vector2(self.position.x + stepSize, yNext);
     *      Vector2 curSlope = after-before;
     *
     *      // If we're descending, let's say the angle equals zero (unless we want a slight acceleration, which is rarely the case)
     *      if (Mathf.Sign(curSlope.y) != Mathf.Sign(graphics.localScale.x)) result = 0;
     *      // When ascending, we must get the angle anyway.
     *      else result = Vector2.Angle(Vector2.right, curSlope);
     *
     *      return result;
     * }
     *
     * // Called when we might hit a ceiling. Same logic as UpdateSlope().
     * bool UpdateCeiling()
     * {
     *      float progress = (self.position.x - ceiling.xMin) / (ceiling.xMax - ceiling.xMin);
     *      progress = Mathf.Clamp01(progress);
     *
     *      float yNeeded = (ceiling.self.position.y + ceiling.verticalOffset - ceiling.zoneHeight) + ceiling.yScale * ceiling.ceilingCurve.Evaluate(progress);
     *
     *      if (top > yNeeded)
     *      {
     *              self.position = new Vector3(self.position.x, yNeeded + topDelta, self.position.z);
     *
     *              if(!collisionFlags.up)
     *              {
     *                      if (onCollisionEnter != null) onCollisionEnter(new RaycastHitPlus());
     *                      if (onVerticalCollisionEnter != null) onVerticalCollisionEnter(new RaycastHitPlus());
     *              }
     *
     *              collisionFlags.up = true;
     *      }
     *      if (self.position.y == yNeeded + topDelta) collisionFlags.up = true;
     *
     *      return top >= yNeeded;
     * }
     * /**/
    #endregion

    #region Movement

    private void MoveHorizontally(ref Vector3 deltaMovement)
    {
        float length       = Mathf.Abs(deltaMovement.x) + skinWidth;
        bool  isGoingRight = deltaMovement.x > 0;

        RayDirection   dir    = isGoingRight ? RayDirection.Right : RayDirection.Left;
        RaycastHitPlus result = raycaster.CastRays(dir, length);

        if (result.box != null)
        {
            // stop the horizontal movement as we bumped into something
            deltaMovement.x = 0;

            // flip the collision flags
            if (isGoingRight)
            {
                collisionFlags.right = true;
            }
            else
            {
                collisionFlags.left = true;
            }

            // And finally, call events
            if (onCollisionEnter != null)
            {
                onCollisionEnter(result);
            }
            if (onHorizontalCollisionEnter != null)
            {
                onHorizontalCollisionEnter(result);
            }
        }
    }
Beispiel #2
0
    public void SetColliding(RayDirection dir, bool state)
    {
        string call = "";

        if (!collisions[dir] && state)
        {
            call = "enter";
        }
        if (collisions[dir] && !state)
        {
            call = "exit";
        }

        collisions[dir] = state;

        switch (call)
        {
        case "enter":
            CollisionEnter();
            break;

        case "exit":
            CollisionExit();
            break;
        }
    }
Beispiel #3
0
    // Update is called once per frame
    void Update()
    {
        // 仰向け
        if (Physics.Raycast(transform.position, transform.forward, m_paramTable.rayDistance, m_mask))
        {
            if (m_rayDirection != RayDirection.Forward)
            {
                m_isDiffDir = true;
            }
            m_rayDirection = RayDirection.Forward;
            m_hitFlg       = true;
        }
        // うつ伏せ
        else if (Physics.Raycast(transform.position, -transform.forward, m_paramTable.rayDistance, m_mask))
        {
            if (m_rayDirection != RayDirection.Back)
            {
                m_isDiffDir = true;
            }
            m_rayDirection = RayDirection.Back;
            m_hitFlg       = true;
        }

        else
        {
            m_hitFlg = false;
        }
    }
Beispiel #4
0
        /** \copydoc Pathfinding::ISerializableObject::DeSerializeSettings */
        public void DeSerializeSettings(AstarSerializer serializer)
        {
            mask.value   = (int)serializer.GetValue("Mask", typeof(int));
            diameter     = (float)serializer.GetValue("Diameter", typeof(float));
            height       = (float)serializer.GetValue("Height", typeof(float));
            type         = (ColliderType)serializer.GetValue("Type", typeof(int));
            rayDirection = (RayDirection)serializer.GetValue("RayDirection", typeof(int));

            heightMask.value     = (int)serializer.GetValue("heightMask", typeof(int), -1);
            fromHeight           = (float)serializer.GetValue("fromHeight", typeof(float), 100.0F);
            thickRaycastDiameter = (float)serializer.GetValue("thickRaycastDiameter", typeof(float));
            thickRaycast         = (bool)serializer.GetValue("thickRaycast", typeof(bool));

            collisionCheck = (bool)serializer.GetValue("collisionCheck", typeof(bool), true);
            heightCheck    = (bool)serializer.GetValue("heightCheck", typeof(bool), true);

            unwalkableWhenNoGround = (bool)serializer.GetValue("unwalkableWhenNoGround", typeof(bool), true);

            collisionOffset = (float)serializer.GetValue("collisionOffset", typeof(float), 0.0F);

            if (fromHeight == 0)
            {
                fromHeight = 100;
            }
        }
Beispiel #5
0
 public RayProperties(Vector3 offset, float angle, float length, bool debug, RayDirection direction)
 {
     Offset        = offset;
     Angle         = angle;
     Length        = length;
     ShowDebugLine = debug;
     Direction     = direction;
 }
Beispiel #6
0
    public bool IsColliding(RayDirection dir)
    {
        if (!collisions.ContainsKey(dir))
        {
            return(false);
        }

        return(collisions[dir]);
    }
 /// <summary>
 /// Write instruction operands into bytecode stream.
 /// </summary>
 /// <param name="writer">Bytecode writer.</param>
 public override void WriteOperands(WordWriter writer)
 {
     RayQuery.Write(writer);
     Accel.Write(writer);
     RayFlags.Write(writer);
     CullMask.Write(writer);
     RayOrigin.Write(writer);
     RayTMin.Write(writer);
     RayDirection.Write(writer);
     RayTMax.Write(writer);
 }
Beispiel #8
0
 /// <summary>
 /// Write instruction operands into bytecode stream.
 /// </summary>
 /// <param name="writer">Bytecode writer.</param>
 public override void WriteOperands(WordWriter writer)
 {
     Accel.Write(writer);
     RayFlags.Write(writer);
     CullMask.Write(writer);
     SBTOffset.Write(writer);
     SBTStride.Write(writer);
     MissIndex.Write(writer);
     RayOrigin.Write(writer);
     RayTmin.Write(writer);
     RayDirection.Write(writer);
     RayTmax.Write(writer);
     PayloadId.Write(writer);
 }
        /// <summary>
        /// Calculate number of words to fit complete instruction bytecode.
        /// </summary>
        /// <returns>Number of words in instruction bytecode.</returns>
        public override uint GetWordCount()
        {
            uint wordCount = 0;

            wordCount += RayQuery.GetWordCount();
            wordCount += Accel.GetWordCount();
            wordCount += RayFlags.GetWordCount();
            wordCount += CullMask.GetWordCount();
            wordCount += RayOrigin.GetWordCount();
            wordCount += RayTMin.GetWordCount();
            wordCount += RayDirection.GetWordCount();
            wordCount += RayTMax.GetWordCount();
            return(wordCount);
        }
Beispiel #10
0
        /// <summary>
        /// Calculate number of words to fit complete instruction bytecode.
        /// </summary>
        /// <returns>Number of words in instruction bytecode.</returns>
        public override uint GetWordCount()
        {
            uint wordCount = 0;

            wordCount += Accel.GetWordCount();
            wordCount += RayFlags.GetWordCount();
            wordCount += CullMask.GetWordCount();
            wordCount += SBTOffset.GetWordCount();
            wordCount += SBTStride.GetWordCount();
            wordCount += MissIndex.GetWordCount();
            wordCount += RayOrigin.GetWordCount();
            wordCount += RayTmin.GetWordCount();
            wordCount += RayDirection.GetWordCount();
            wordCount += RayTmax.GetWordCount();
            wordCount += PayloadId.GetWordCount();
            return(wordCount);
        }
Beispiel #11
0
 public void DeserializeSettings(GraphSerializationContext ctx)
 {
     this.type                   = (ColliderType)ctx.reader.ReadInt32();
     this.diameter               = ctx.reader.ReadSingle();
     this.height                 = ctx.reader.ReadSingle();
     this.collisionOffset        = ctx.reader.ReadSingle();
     this.rayDirection           = (RayDirection)ctx.reader.ReadInt32();
     this.mask                   = ctx.reader.ReadInt32();
     this.heightMask             = ctx.reader.ReadInt32();
     this.fromHeight             = ctx.reader.ReadSingle();
     this.thickRaycast           = ctx.reader.ReadBoolean();
     this.thickRaycastDiameter   = ctx.reader.ReadSingle();
     this.unwalkableWhenNoGround = ctx.reader.ReadBoolean();
     this.use2D                  = ctx.reader.ReadBoolean();
     this.collisionCheck         = ctx.reader.ReadBoolean();
     this.heightCheck            = ctx.reader.ReadBoolean();
 }
Beispiel #12
0
        public void DeserializeSettingsCompatibility(GraphSerializationContext ctx)
        {
            type                 = (ColliderType)ctx.reader.ReadInt32();
            diameter             = ctx.reader.ReadSingle();
            height               = ctx.reader.ReadSingle();
            collisionOffset      = ctx.reader.ReadSingle();
            rayDirection         = (RayDirection)ctx.reader.ReadInt32();
            mask                 = (LayerMask)ctx.reader.ReadInt32();
            heightMask           = (LayerMask)ctx.reader.ReadInt32();
            fromHeight           = ctx.reader.ReadSingle();
            thickRaycast         = ctx.reader.ReadBoolean();
            thickRaycastDiameter = ctx.reader.ReadSingle();

            unwalkableWhenNoGround = ctx.reader.ReadBoolean();
            use2D          = ctx.reader.ReadBoolean();
            collisionCheck = ctx.reader.ReadBoolean();
            heightCheck    = ctx.reader.ReadBoolean();
        }
 public bool Check(Vector3 position)
 {
     if (!this.collisionCheck)
     {
         return(true);
     }
     if (this.use2D)
     {
         ColliderType colliderType = this.type;
         if (colliderType == ColliderType.Sphere)
         {
             return(Physics2D.OverlapCircle(position, this.finalRadius, this.mask) == null);
         }
         if (colliderType == ColliderType.Capsule)
         {
             throw new Exception("Capsule mode cannot be used with 2D since capsules don't exist in 2D. Please change the Physics Testing -> Collider Type setting.");
         }
         return(Physics2D.OverlapPoint(position, this.mask) == null);
     }
     else
     {
         position += this.up * this.collisionOffset;
         ColliderType colliderType = this.type;
         if (colliderType == ColliderType.Sphere)
         {
             return(!Physics.CheckSphere(position, this.finalRadius, this.mask));
         }
         if (colliderType == ColliderType.Capsule)
         {
             return(!Physics.CheckCapsule(position, position + this.upheight, this.finalRadius, this.mask));
         }
         RayDirection rayDirection = this.rayDirection;
         if (rayDirection == RayDirection.Up)
         {
             return(!Physics.Raycast(position, this.up, this.height, this.mask));
         }
         if (rayDirection == RayDirection.Both)
         {
             return(!Physics.Raycast(position, this.up, this.height, this.mask) && !Physics.Raycast(position + this.upheight, -this.up, this.height, this.mask));
         }
         return(!Physics.Raycast(position + this.upheight, -this.up, this.height, this.mask));
     }
 }
Beispiel #14
0
    // Update is called once per frame
    void Update()
    {
        RaycastHit hit;

        if (Physics.Raycast(transform.position, transform.forward, rayDistance, mask))
        {
//            Debug.Log("前");
            rayDirection = RayDirection.Forward;
            hitFlg       = true;
        }
        else if (Physics.Raycast(transform.position, -transform.forward, rayDistance, mask))
        {
//            Debug.Log("後ろ");
            rayDirection = RayDirection.Back;
            hitFlg       = true;
        }
        else
        {
            hitFlg = false;
        }
    }
    //Sets dir based on given rayDirection - Jak
    void AssignRayDirection(RayDirection rayDirection, ref Vector3 dir, ref Vector3 startpos)
    {
        float length = 3;

        switch (rayDirection)
        {
        case RayDirection.FORWARD:
            dir = transform.forward * length;
            //startpos.z = startpos.z + GetComponent<Collider>().bounds.extents.z;
            break;

        case RayDirection.BACK:
            dir = -transform.forward * length;
            //startpos.z = startpos.z - GetComponent<Collider>().bounds.extents.z * 2;
            break;

        case RayDirection.LEFT:
            dir = -transform.right * length;
            //startpos.x = startpos.x -GetComponent<Collider>().bounds.extents.x * 2;
            break;

        case RayDirection.RIGHT:
            dir = transform.right * length;
            //startpos.x = startpos.x + GetComponent<Collider>().bounds.extents.x * 2;
            break;

        case RayDirection.UP:
            dir = transform.up * length;
            //startpos.y = startpos.y + GetComponent<Collider>().bounds.extents.y * 2;
            break;

        case RayDirection.DOWN:
            dir = -transform.up * length;
            //startpos.y = startpos.y - GetComponent<Collider>().bounds.extents.y * 2;
            break;

        default:
            break;
        }
    }
Beispiel #16
0
    public void Spawn(Vector3 position, RayDirection direction)
    {
        transform.position = position;

        _rayObject.SetActive(false);
        var zRotation = 0f;

        switch (direction)
        {
        case RayDirection.Up: break;

        case RayDirection.Down: zRotation = 180f; break;

        case RayDirection.Left: zRotation = 90f; break;

        case RayDirection.Right: zRotation = -90f; break;
        }

        _rayObject.transform.localRotation = Quaternion.Euler(0f, 0f, zRotation);

        _timer.StartCountDown(_waitTime, ShootRay);
    }
 // Token: 0x060024D4 RID: 9428 RVA: 0x0019D374 File Offset: 0x0019B574
 public bool Check(Vector3 position)
 {
     if (!this.collisionCheck)
     {
         return(true);
     }
     if (this.use2D)
     {
         ColliderType colliderType = this.type;
         if (colliderType <= ColliderType.Capsule)
         {
             return(Physics2D.OverlapCircle(position, this.finalRadius, this.mask) == null);
         }
         return(Physics2D.OverlapPoint(position, this.mask) == null);
     }
     else
     {
         position += this.up * this.collisionOffset;
         ColliderType colliderType = this.type;
         if (colliderType == ColliderType.Sphere)
         {
             return(!Physics.CheckSphere(position, this.finalRadius, this.mask, QueryTriggerInteraction.Collide));
         }
         if (colliderType == ColliderType.Capsule)
         {
             return(!Physics.CheckCapsule(position, position + this.upheight, this.finalRadius, this.mask, QueryTriggerInteraction.Collide));
         }
         RayDirection rayDirection = this.rayDirection;
         if (rayDirection == RayDirection.Up)
         {
             return(!Physics.Raycast(position, this.up, this.height, this.mask, QueryTriggerInteraction.Collide));
         }
         if (rayDirection == RayDirection.Both)
         {
             return(!Physics.Raycast(position, this.up, this.height, this.mask, QueryTriggerInteraction.Collide) && !Physics.Raycast(position + this.upheight, -this.up, this.height, this.mask, QueryTriggerInteraction.Collide));
         }
         return(!Physics.Raycast(position + this.upheight, -this.up, this.height, this.mask, QueryTriggerInteraction.Collide));
     }
 }
Beispiel #18
0
    private void MoveVertically(ref Vector3 deltaMovement)
    {
        //if (disableVerticalPhysics) return;

        bool  isGoingUp = deltaMovement.y > 0;
        float length    = Mathf.Abs(deltaMovement.y) + skinWidth;

        RayDirection   dir    = isGoingUp ? RayDirection.Up : RayDirection.Down;
        RaycastHitPlus result = raycaster.CastRays(dir, length, false);

        if (result.box)
        {
            // set our new deltaMovement and recalculate the rayDistance taking it into account
            deltaMovement.y = result.hit.point.y - result.ray.y;

            // remember to remove the skinWidth from our deltaMovement
            if (isGoingUp)
            {
                deltaMovement.y  -= skinWidth;
                collisionFlags.up = true;
            }
            else
            {
                deltaMovement.y    += skinWidth;
                collisionFlags.down = true;
            }

            // Watch out, the global event could be called twice (one for horizontal movement, one for vertical movement).
            if (onCollisionEnter != null)
            {
                onCollisionEnter(result);
            }
            if (onVerticalCollisionEnter != null)
            {
                onVerticalCollisionEnter(result);
            }
        }
    }
Beispiel #19
0
    private bool DetectCollisions(RayDirection direction)
    {
        Vector2 startingPoint;
        Vector2 endingPoint;
        Vector2 rayDirection;
        float   rayDistance;

        switch (direction)
        {
        case RayDirection.Down:
            if (velocity.y > 0)
            {
                return(false);
            }
            rayDirection  = Vector2.down;
            startingPoint = new Vector2(collider.bounds.min.x, collider.bounds.min.y);
            endingPoint   = new Vector2(collider.bounds.max.x, collider.bounds.min.y);
            rayDistance   = Mathf.Abs(velocity.y) * Time.fixedDeltaTime;
            break;

        case RayDirection.Up:
            if (velocity.y < 0)
            {
                return(false);
            }
            rayDirection  = Vector2.up;
            startingPoint = new Vector2(collider.bounds.min.x, collider.bounds.max.y);
            endingPoint   = new Vector2(collider.bounds.max.x, collider.bounds.max.y);
            rayDistance   = Mathf.Abs(velocity.y) * Time.fixedDeltaTime;
            break;

        case RayDirection.Right:
            if (velocity.x < 0)
            {
                return(false);
            }
            rayDirection  = Vector2.right;
            startingPoint = new Vector2(collider.bounds.max.x, collider.bounds.min.y);
            endingPoint   = new Vector2(collider.bounds.max.x, collider.bounds.max.y);
            rayDistance   = Mathf.Abs(velocity.x) * Time.fixedDeltaTime;
            break;

        case RayDirection.Left:
            if (velocity.x > 0)
            {
                return(false);
            }
            rayDirection  = Vector2.left;
            startingPoint = new Vector2(collider.bounds.min.x, collider.bounds.min.y);
            endingPoint   = new Vector2(collider.bounds.min.x, collider.bounds.max.y);
            rayDistance   = Mathf.Abs(velocity.x) * Time.fixedDeltaTime;
            break;

        default:
            return(false);
        }
        rayDistance += collisionBuffer;
        if (collisionBuffer > skinBuffer)
        {
            rayDistance -= skinBuffer;
        }

        float raySpacing = 1f / (raycastResolution * Vector2.Distance(startingPoint, endingPoint));

        bool isHit    = false;
        bool stepping = false;

        for (float t = 0; t <= 1; t += raySpacing)
        {
            float        stepDistance = -Mathf.Abs(raycastResolution * t - raycastResolution / 2f) + raycastResolution / 2f;;
            Vector2      origin       = Vector2.Lerp(startingPoint, endingPoint, t) + (rayDirection * skinBuffer);
            RaycastHit2D hit          = Physics2D.Raycast(origin, rayDirection, rayDistance);

            if (hit && !hit.collider.isTrigger)
            {
                //we collided
                //handle step physics
                if (rayDirection.x != 0 && Mathf.Sign(rayDirection.x) == Mathf.Sign(velocity.x))
                {
                    if (stepDistance < stepSize)
                    {
                        //Start step check
                        stepping = true;
                    }
                    else
                    {
                        stepping = false;
                    }
                }

                if (!stepping)
                {
                    //regulate velocity based on collision
                    Vector2 tempVelocity = velocity;
                    velocity = rayDirection * hit.distance / Time.fixedDeltaTime;
                    if (rayDirection.x == 0)
                    {
                        velocity.x = tempVelocity.x;
                    }
                    if (rayDirection.y == 0)
                    {
                        velocity.y = tempVelocity.y;
                    }
                }


                isHit = true;
            }
            else if (stepping && stepCoroutine == null && stepDistance <= stepSize && IsColliding(RayDirection.Down))
            {
                //Step
                transform.position += Vector3.up * (1f / raycastResolution) * (stepDistance - (1f / raycastResolution) - 0.01f);
                stepping            = false;
            }
        }

        return(isHit);
    }
Beispiel #20
0
		public void DeserializeSettings ( GraphSerializationContext ctx ) {
			type = (ColliderType)ctx.reader.ReadInt32();
			diameter = ctx.reader.ReadSingle ();
			height = ctx.reader.ReadSingle ();
			collisionOffset = ctx.reader.ReadSingle ();
			rayDirection = (RayDirection)ctx.reader.ReadInt32 ();
			mask = (LayerMask)ctx.reader.ReadInt32 ();
			heightMask = (LayerMask)ctx.reader.ReadInt32 ();
			fromHeight = ctx.reader.ReadSingle ();
			thickRaycast = ctx.reader.ReadBoolean ();
			thickRaycastDiameter = ctx.reader.ReadSingle ();

			unwalkableWhenNoGround = ctx.reader.ReadBoolean();
			use2D = ctx.reader.ReadBoolean();
			collisionCheck = ctx.reader.ReadBoolean();
			heightCheck = ctx.reader.ReadBoolean();
		}
Beispiel #21
0
        /** \copydoc Pathfinding::ISerializableObject::DeSerializeSettings */
        public void DeSerializeSettings(AstarSerializer serializer)
        {
            mask.value = (int)serializer.GetValue ("Mask",typeof (int));
            diameter = (float)serializer.GetValue ("Diameter",typeof (float));
            height = (float)serializer.GetValue ("Height",typeof (float));
            type = (ColliderType)serializer.GetValue ("Type",typeof(int));
            rayDirection = (RayDirection)serializer.GetValue ("RayDirection",typeof(int));

            heightMask.value = (int)serializer.GetValue ("heightMask",typeof (int),-1);
            fromHeight = (float)serializer.GetValue ("fromHeight",typeof (float), 100.0F);
            thickRaycastDiameter = (float)serializer.GetValue ("thickRaycastDiameter",typeof (float));
            thickRaycast = (bool)serializer.GetValue ("thickRaycast",typeof (bool));

            collisionCheck = (bool)serializer.GetValue ("collisionCheck",typeof(bool),true);
            heightCheck = (bool)serializer.GetValue ("heightCheck",typeof(bool),true);

            unwalkableWhenNoGround = (bool)serializer.GetValue ("unwalkableWhenNoGround",typeof(bool),true);

            collisionOffset = (float)serializer.GetValue ("collisionOffset",typeof(float),0.0F);

            if (fromHeight == 0) fromHeight = 100;
        }
Beispiel #22
0
    private void InspectCell(HashSet <GameCell> resultCells, HashSet <Bomb> bombs, int cellX, int cellY, RayDirection direction, int rangeLeft)
    {
        if (rangeLeft > 0)
        {
            GameCell cell = levelManager.GetBoard().GetGameCell(cellX, cellY);
            if (IsGameCellDestructible(cell))
            {
                resultCells.Add(cell);

                // explode other bombs in range
                if (cell.bomb != null && !bombs.Contains(cell.bomb))
                {
                    bombs.Add(cell.bomb);
                    int bombRange = cell.bomb.explosionRange;
                    InspectCell(resultCells, bombs, cellX - 1, cellY, RayDirection.LEFT, bombRange);
                    InspectCell(resultCells, bombs, cellX, cellY + 1, RayDirection.UP, bombRange);
                    InspectCell(resultCells, bombs, cellX + 1, cellY, RayDirection.RIGHT, bombRange);
                    InspectCell(resultCells, bombs, cellX, cellY - 1, RayDirection.BOTTOM, bombRange);
                }

                if (IsGameCellRangeTransparent(cell))
                {
                    switch (direction)
                    {
                    case RayDirection.LEFT:
                        InspectCell(resultCells, bombs, cellX - 1, cellY, direction, rangeLeft - 1);
                        break;

                    case RayDirection.UP:
                        InspectCell(resultCells, bombs, cellX, cellY + 1, direction, rangeLeft - 1);
                        break;

                    case RayDirection.RIGHT:
                        InspectCell(resultCells, bombs, cellX + 1, cellY, direction, rangeLeft - 1);
                        break;

                    case RayDirection.BOTTOM:
                        InspectCell(resultCells, bombs, cellX, cellY - 1, direction, rangeLeft - 1);
                        break;
                    }
                }
            }
        }
    }
Beispiel #23
0
    public RaycastHitPlus CastRays(RayDirection dir, float length, bool dontrefreshRayOrigins = false)
    {
        _outcome.box = null;

        if (!dontrefreshRayOrigins)
        {
            RefreshRayOrigins();
        }

        float   rayDistance      = Mathf.Abs(length) + skinWidth;
        Vector2 rayDirection     = Vector2.zero;
        Vector2 initialRayOrigin = Vector2.zero;

        if (dir == RayDirection.Down)
        {
            rayDirection     = Vector2.down;
            initialRayOrigin = _origins.bottomLeft;
        }
        if (dir == RayDirection.Up)
        {
            rayDirection     = Vector2.up;
            initialRayOrigin = _origins.topLeft;
        }
        if (dir == RayDirection.Left)
        {
            rayDirection     = Vector2.left;
            initialRayOrigin = _origins.bottomLeft;
        }
        if (dir == RayDirection.Right)
        {
            rayDirection     = Vector2.right;
            initialRayOrigin = _origins.bottomRight;
        }

        // To sum it up : if direction is UP or DOWN, we cast rays from left to right.
        // If direction is LEFT or RIGHT, we cast rays from bottom to top.

        int   totalRays       = horizontalRays;
        bool  isVerticalRay   = (dir == RayDirection.Down || dir == RayDirection.Up);
        float horizontalDelta = isVerticalRay ? horizontalDistBetweenRays : 0;
        float verticalDelta   = isVerticalRay ? 0 : verticalDistBetweenRays;

        for (var i = 0; i < totalRays; i++)
        {
            _outcome.ray = new Vector2(initialRayOrigin.x + i * horizontalDelta, initialRayOrigin.y + i * verticalDelta);

#if UNITY_EDITOR
            if (drawRaysInEditor)
            {
                Debug.DrawRay(_outcome.ray, rayDirection, Color.red);
            }
#endif

            string formerLayerName = LayerMask.LayerToName(gameObject.layer);
            gameObject.layer = emptyLayerIndex;
            _outcome.hit     = Physics2D.Raycast(_outcome.ray, rayDirection, rayDistance, collidableLayers);
            gameObject.layer = LayerMask.NameToLayer(formerLayerName);

            if (_outcome.hit.collider != null)
            {
                // We don't want to hit triggers.
                if (_outcome.hit.collider.isTrigger)
                {
                    continue;
                }

                // One-way platforms are negated whenever the controller isn't falling on them (i.e. going down)
                if (dir != RayDirection.Down)
                {
                    if ((1 << _outcome.hit.collider.gameObject.layer & oneWayLayers) > 0)
                    {
                        continue;
                    }
                }

                // If we passed all those checks, we're good.
                _outcome.box = _outcome.hit.collider;
                return(_outcome);
            }
        }

        return(_outcome);
    }