Beispiel #1
0
    //点和圆碰撞
    public static bool CollidePointAndCircle(GameVector2 _p, GameVector2 _c, int _radius)
    {
        long sprRadius   = _radius * _radius;
        long sqrDistance = _c.sqrMagnitude(_p);

        return(sqrDistance < sprRadius);
    }
Beispiel #2
0
    //圆和圆碰撞
    public static bool CollideCircleAndCircle(GameVector2 _c1, GameVector2 _c2, int _radius1, int _radius2)
    {
        int  sumRadius   = _radius1 + _radius2;
        long sprRadius   = sumRadius * sumRadius;
        long sqrDistance = _c1.sqrMagnitude(_c2);

        return(sqrDistance < sprRadius);
    }
Beispiel #3
0
    // 圆和正圆扇面的碰撞,不带位置修正
    public static bool CollideCircleAndArcArea(GameVector2 _c1, int _radius1, GameVector2 _arcCen, int _arcRadius, int _arcAngle, int _arcAngleSize)
    {
        int  radiusSum    = _radius1 + _arcRadius;
        long sqrRadiusSum = radiusSum * radiusSum;
        long sqrDistance  = _c1.sqrMagnitude(_arcCen);

        if (sqrDistance >= sqrRadiusSum)
        {
            return(false);
        }
        int _angle       = (_c1 - _arcCen).Angle();
        int _point1Angle = _arcAngle + _arcAngleSize;
        int _point2Angle = _arcAngle - _arcAngleSize;

        bool inArc;

        if (_point2Angle < 0)
        {
            int _angle1 = (int)Mathf.Repeat(_angle - _point2Angle, 360f);
            if (_angle1 >= 0 && _angle1 <= (_point1Angle - _point2Angle))
            {
                inArc = true;
            }
            else
            {
                inArc = false;
            }
        }
        else if (_point1Angle > 360)
        {
            int _delA   = _point1Angle - 360;
            int _angle1 = (int)Mathf.Repeat(_angle - _delA, 360f);
            if (_angle1 >= (_point2Angle - _delA) && _angle1 <= 360)
            {
                inArc = true;
            }
            else
            {
                inArc = false;
            }
        }
        else
        {
            if (_angle >= _point2Angle && _angle <= _point1Angle)
            {
                inArc = true;
            }
            else
            {
                inArc = false;
            }
        }
        if (inArc)
        {
            return(true);
        }
        return(false);
    }
Beispiel #4
0
    /// <summary>
    ///	点和圆的碰撞,圆不动修正点的位置
    /// </summary>
    /// <returns><c>true</c>, if point and circle was collided, <c>false</c> otherwise.</returns>
    /// <param name="_p">碰撞点.</param>
    /// <param name="_c">碰撞圆心.</param>
    /// <param name="_radius">圆半径.</param>
    /// <param name="_amend">修正值.</param>
    public static bool CollidePointAndCircle(GameVector2 _p, GameVector2 _c, int _radius, out GameVector2 _amend)
    {
        _amend = GameVector2.zero;

        long sprRadius = _radius * _radius;

        long sqrDistance = _c.sqrMagnitude(_p);

        if (sqrDistance >= sprRadius)
        {
            return(false);
        }

        int distance = (int)Mathf.Sqrt(sqrDistance);
        int _angle   = (_p - _c).Angle();
        int amendDis = 1 + (_radius - distance) / 100;

        _amend = amendDis * BattleData.Instance.GetSpeed(_angle);
        return(true);
    }
Beispiel #5
0
    // 圆和正圆弧的碰撞,不带位置修正
    public static bool CollideCircleAndArc(GameVector2 _c1, int _radius1, GameVector2 _arcCen, int _arcRadius, int _arcAngle, int _arcAngleSize)
    {
        int  radiusSum    = _radius1 + _arcRadius;
        long sqrRadiusSum = radiusSum * radiusSum;
        long sqrDistance  = _c1.sqrMagnitude(_arcCen);

        if (sqrDistance >= sqrRadiusSum)
        {
            return(false);
        }
        int  radiusDel    = _radius1 - _arcRadius;
        long sqrRadiusDel = radiusDel * radiusDel;

        if (sqrDistance <= sqrRadiusDel)
        {
            return(false);
        }
        int _angle = (_c1 - _arcCen).Angle();

        if (Mathf.Abs(_angle - _arcAngle) <= _arcAngleSize)
        {
            return(true);
        }
        int         _point1Angle = (int)Mathf.Repeat(_arcAngle + _arcAngleSize, 360);
        GameVector2 _point1      = _arcCen + (_arcRadius / 100) * BattleData.Instance.GetSpeed(_point1Angle);
        bool        _result1     = ToolGameVector.CollidePointAndCircle(_c1, _point1, _radius1);

        if (_result1)
        {
            return(_result1);
        }
        int         _point2Angle = (int)Mathf.Repeat(_arcAngle - _arcAngleSize, 360);
        GameVector2 _point2      = _arcCen + (_arcRadius / 100) * BattleData.Instance.GetSpeed(_point2Angle);
        bool        _result2     = ToolGameVector.CollidePointAndCircle(_c1, _point2, _radius1);

        if (_result2)
        {
            return(_result2);
        }
        return(false);
    }
Beispiel #6
0
    /// <summary>
    /// 圆和圆的碰撞,2个圆的位置都修正
    /// </summary>
    /// <returns><c>true</c>, if circle and circle was collided, <c>false</c> otherwise.</returns>
    /// <param name="_c1">圆1的圆心.</param>
    /// <param name="_c2">圆2的圆心.</param>
    /// <param name="_radius1">圆1的半径.</param>
    /// <param name="_radius2">圆2的半径.</param>
    /// <param name="_amend1">圆1的修正值.</param>
    /// <param name="_amend2">圆2的修正值.</param>
    public static bool CollideCircleAndCircle(GameVector2 _c1, GameVector2 _c2, int _radius1, int _radius2, out GameVector2 _amend1, out GameVector2 _amend2)
    {
        _amend1 = GameVector2.zero;
        _amend2 = GameVector2.zero;

        int  radiusSum = _radius1 + _radius2;
        long sprRadius = radiusSum * radiusSum;

        long sqrDistance = _c1.sqrMagnitude(_c2);

        if (sqrDistance >= sprRadius)
        {
            return(false);
        }

        int distance = (int)Mathf.Sqrt(sqrDistance);
        int _angle   = (_c1 - _c2).Angle();
        int amendDis = 1 + (int)((radiusSum - distance) * 0.5) / 100;

        _amend1 = amendDis * BattleData.Instance.GetSpeed(_angle);
        _amend2 = -1 * _amend1;

        return(true);
    }
Beispiel #7
0
 public static bool IsInDistance(GameVector2 _pos1, GameVector2 _pos2, long _distance, out long _realdis)
 {
     _realdis = _pos1.sqrMagnitude(_pos2);
     return(_realdis <= _distance * _distance);
 }
Beispiel #8
0
    /// <summary>
    /// 圆和正圆扇面的碰撞,带位置修正
    /// </summary>
    /// <returns><c>true</c>, if circle and arc was collided, <c>false</c> otherwise.</returns>
    /// <param name="_c1">圆心.</param>
    /// <param name="_radius1">圆半径.</param>
    /// <param name="_arcCen">扇面圆心.</param>
    /// <param name="_arcRadius">扇面所在圆半径.</param>
    /// <param name="_arcAngle">角度.</param>
    /// <param name="_arcAngleSize">角度范围.</param>
    /// <param name="_amend">修正值.</param>
    public static bool CollideCircleAndArcArea(GameVector2 _c1, int _radius1, GameVector2 _arcCen, int _arcRadius, int _arcAngle, int _arcAngleSize, out GameVector2 _amend)
    {
        _amend = GameVector2.zero;
        int  radiusSum    = _radius1 + _arcRadius;
        long sqrRadiusSum = radiusSum * radiusSum;
        long sqrDistance  = _c1.sqrMagnitude(_arcCen);

        if (sqrDistance >= sqrRadiusSum)
        {
            return(false);
        }
        int  _angle       = (_c1 - _arcCen).Angle();
        int  _point1Angle = _arcAngle + _arcAngleSize;
        int  _point2Angle = _arcAngle - _arcAngleSize;
        bool inArc;

        if (_point2Angle < 0)
        {
            int _angle1 = (int)Mathf.Repeat(_angle - _point2Angle, 360f);
            if (_angle1 >= 0 && _angle1 <= (_point1Angle - _point2Angle))
            {
                inArc = true;
            }
            else
            {
                inArc = false;
            }
        }
        else if (_point1Angle > 360)
        {
            int _delA   = _point1Angle - 360;
            int _angle1 = (int)Mathf.Repeat(_angle - _delA, 360f);
            if (_angle1 >= (_point2Angle - _delA) && _angle1 <= 360)
            {
                inArc = true;
            }
            else
            {
                inArc = false;
            }
        }
        else
        {
            if (_angle >= _point2Angle && _angle <= _point1Angle)
            {
                inArc = true;
            }
            else
            {
                inArc = false;
            }
        }
        if (inArc)
        {
            //在圆弧内,需要修正
            int distance = (int)Mathf.Sqrt(sqrDistance);
            int amendDis = 1 + (int)(radiusSum - distance) / 100;
            _amend = amendDis * BattleData.Instance.GetSpeed(_angle);
            return(true);
        }
        //线段修正
        Vector3 _circleCenter  = ToolGameVector.ChangeGameVectorToVector3(_c1);
        Vector3 _arcAreaCenter = ToolGameVector.ChangeGameVectorToVector3(_arcCen);

        _point1Angle = (int)Mathf.Repeat(_point1Angle, 360);
        GameVector2 _point1 = _arcCen + (_arcRadius / 100) * BattleData.Instance.GetSpeed(_point1Angle);

        _point2Angle = (int)Mathf.Repeat(_point2Angle, 360);
        GameVector2 _point2 = _arcCen + (_arcRadius / 100) * BattleData.Instance.GetSpeed(_point2Angle);

        Vector3 _line1Point = ToolGameVector.ChangeGameVectorToVector3(_point1);
        Vector3 _line2Point = ToolGameVector.ChangeGameVectorToVector3(_point2);
        //线段1修正
        bool        amendline1  = false;
        GameVector2 amendLine1P = GameVector2.zero;
        Vector3     _circleVec  = _circleCenter - _arcAreaCenter;
        Vector3     _line       = _line1Point - _arcAreaCenter;
        Vector3     _cross      = Vector3.Cross(_circleVec, _line);

        if (_cross.z <= 0)
        {
            //在线段的左侧,即多边形的外侧
            Vector3 vecProj    = Vector3.Project(_circleVec, _line);          //投影点
            float   disLine    = _line.magnitude;
            float   proj_begin = vecProj.magnitude;
            float   proj_end   = (vecProj - _line).magnitude;
            float   projlengh  = proj_begin + proj_end;
            if ((disLine + 1) >= projlengh)
            {
                //投影在线段上
                int dis       = (int)Mathf.Sqrt(_circleVec.sqrMagnitude - vecProj.sqrMagnitude);
                int disRadius = _radius1 / 100;
                if (dis < disRadius)
                {
                    //需要修正
                    amendline1 = true;
                    int     amendDis   = 1 + (int)(_radius1 / 100 - dis);
                    Vector3 angelVec   = _circleVec - vecProj;
                    float   angle1     = Mathf.Atan2(angelVec.y, angelVec.x) * Mathf.Rad2Deg;
                    int     amendAngle = (int)Mathf.Repeat(angle1, 360f);
                    amendLine1P = amendDis * BattleData.Instance.GetSpeed(amendAngle);
                }
            }
            else
            {
                //投影不在当前线段上
            }
        }
        //线段2修正
        bool        amendline2  = false;
        GameVector2 amendLine2P = GameVector2.zero;
        Vector3     _circleVec2 = _circleCenter - _line2Point;
        Vector3     _line2      = _arcAreaCenter - _line2Point;
        Vector3     _cross2     = Vector3.Cross(_circleVec2, _line2);

        if (_cross2.z <= 0)
        {
            //在线段的左侧,即多边形的外侧
            Vector3 vecProj    = Vector3.Project(_circleVec2, _line2);          //投影点
            float   disLine    = _line2.magnitude;
            float   proj_begin = vecProj.magnitude;
            float   proj_end   = (vecProj - _line2).magnitude;
            float   projlengh  = proj_begin + proj_end;
            if ((disLine + 1) >= projlengh)
            {
                //投影在线段上

                int dis       = (int)Mathf.Sqrt(_circleVec2.sqrMagnitude - vecProj.sqrMagnitude);
                int disRadius = _radius1 / 100;
                if (dis < disRadius)
                {
                    //需要修正
                    amendline2 = true;
                    int     amendDis   = 1 + (int)(_radius1 / 100 - dis);
                    Vector3 angelVec   = _circleVec2 - vecProj;
                    float   angle1     = Mathf.Atan2(angelVec.y, angelVec.x) * Mathf.Rad2Deg;
                    int     amendAngle = (int)Mathf.Repeat(angle1, 360f);
                    amendLine2P = amendDis * BattleData.Instance.GetSpeed(amendAngle);
                }
            }
            else
            {
                //投影不在当前线段上
            }
        }
        if (amendline1 || amendline2)
        {
            _amend = amendLine1P + amendLine2P;
            return(true);
        }
        //对点修正
        GameVector2 _outAmend1;
        bool        _result1 = ToolGameVector.CollidePointAndCircle(_c1, _arcCen, _radius1, out _outAmend1);

        if (_result1)
        {
            _amend = _outAmend1;
            return(true);
        }
        GameVector2 _outAmend2;
        bool        _result2 = ToolGameVector.CollidePointAndCircle(_c1, _point1, _radius1, out _outAmend2);

        GameVector2 _outAmend3;
        bool        _result3 = ToolGameVector.CollidePointAndCircle(_c1, _point2, _radius1, out _outAmend3);

        if (_result2 || _result3)
        {
            _amend = _outAmend2 + _outAmend3;
            return(true);
        }
        return(false);
    }
Beispiel #9
0
    /// <summary>
    /// 圆和正圆弧的碰撞,带位置修正
    /// </summary>
    /// <returns><c>true</c>, if circle and arc was collided, <c>false</c> otherwise.</returns>
    /// <param name="_c1">圆心.</param>
    /// <param name="_radius1">圆半径.</param>
    /// <param name="_arcCen">圆弧圆心.</param>
    /// <param name="_arcRadius">圆弧所在圆半径.</param>
    /// <param name="_arcAngle">角度.</param>
    /// <param name="_arcAngleSize">角度范围.</param>
    /// <param name="_amend">修正值.</param>
    public static bool CollideCircleAndArc(GameVector2 _c1, int _radius1, GameVector2 _arcCen, int _arcRadius, int _arcAngle, int _arcAngleSize, out GameVector2 _amend)
    {
        _amend = GameVector2.zero;
        int  radiusSum    = _radius1 + _arcRadius;
        long sqrRadiusSum = radiusSum * radiusSum;
        long sqrDistance  = _c1.sqrMagnitude(_arcCen);

        if (sqrDistance >= sqrRadiusSum)
        {
            return(false);
        }
        int  radiusDel    = _radius1 - _arcRadius;
        long sqrRadiusDel = radiusDel * radiusDel;

        if (sqrDistance <= sqrRadiusDel)
        {
            return(false);
        }
        int  _angle       = (_c1 - _arcCen).Angle();
        int  _point1Angle = _arcAngle + _arcAngleSize;
        int  _point2Angle = _arcAngle - _arcAngleSize;
        bool inArc;

        if (_point2Angle < 0)
        {
            int _angle1 = (int)Mathf.Repeat(_angle - _point2Angle, 360f);
            if (_angle1 >= 0 && _angle1 <= (_point1Angle - _point2Angle))
            {
                inArc = true;
            }
            else
            {
                inArc = false;
            }
        }
        else if (_point1Angle > 360)
        {
            int _delA   = _point1Angle - 360;
            int _angle1 = (int)Mathf.Repeat(_angle - _delA, 360f);
            if (_angle1 >= (_point2Angle - _delA) && _angle1 <= 360)
            {
                inArc = true;
            }
            else
            {
                inArc = false;
            }
        }
        else
        {
            if (_angle >= _point2Angle && _angle <= _point1Angle)
            {
                inArc = true;
            }
            else
            {
                inArc = false;
            }
        }
        if (inArc)
        {
            //在圆弧内,需要修正
            long _arcRadiusSqr = _arcRadius * _arcRadius;
            int  distance      = (int)Mathf.Sqrt(sqrDistance);
            int  amendDis;
            int  amendAngle;
            if (sqrDistance >= _arcRadiusSqr)
            {
                //向外修正
                amendDis   = 1 + (int)(radiusSum - distance) / 100;
                amendAngle = _angle;
            }
            else
            {
                amendDis   = 1 + (int)(distance - Mathf.Abs(radiusDel)) / 100;
                amendAngle = (_arcCen - _c1).Angle();
            }
            _amend = amendDis * BattleData.Instance.GetSpeed(amendAngle);
            return(true);
        }

        _point1Angle = (int)Mathf.Repeat(_point1Angle, 360);
        GameVector2 _point1 = _arcCen + (_arcRadius / 100) * BattleData.Instance.GetSpeed(_point1Angle);

        GameVector2 _outAmend1;
        bool        _result1 = ToolGameVector.CollidePointAndCircle(_c1, _point1, _radius1, out _outAmend1);

        if (_result1)
        {
            _amend = _outAmend1;
            return(_result1);
        }

        _point2Angle = (int)Mathf.Repeat(_point2Angle, 360);
        GameVector2 _point2 = _arcCen + (_arcRadius / 100) * BattleData.Instance.GetSpeed(_point2Angle);

        GameVector2 _outAmend2;
        bool        _result2 = ToolGameVector.CollidePointAndCircle(_c1, _point2, _radius1, out _outAmend2);

        if (_result2)
        {
            _amend = _outAmend2;
            return(_result2);
        }
        return(false);
    }
Beispiel #10
0
 public static bool IsInDistance(GameVector2 _pos1, GameVector2 _pos2, long _distance)
 {
     return(_pos1.sqrMagnitude(_pos2) <= _distance * _distance);
 }