Esempio n. 1
0
        //检测是否可以停到球
        public static bool checkCatchingBall(FBActor actor)
        {
            if (actor.world.ball.owner != null || actor.world.ball.willBeCatched)
            {
                return(false);
            }

            //球速度不能为0也不能太大
            var ballSquareSpeed = actor.world.ball.particleVelocity.squareLength;

            if (ballSquareSpeed == Fix64.Zero || ballSquareSpeed > actor.configuration.scb_maxBallSpeed.square)
            {
                //Debuger.Log("Speed too big " + (float)ballSquareSpeed);
                return(false);
            }
            //球员速度不能太快
            if (actor.particle.velocity.squareLength > actor.configuration.scb_maxActorSpeed.square)
            {
                //Debuger.Log("Actor too quick to get ball" + (float)actor.particle.velocity.squareLength);
                return(false);
            }

            //求出足球方向和检测半径是否有交点
            Fix64 ballSpeedLength = actor.world.ball.particleVelocity.length;

            FixVector2 ballActor = actor.world.ball.getPosition() - actor.getPosition();
            Fix64      dot       = FixVector2.dot(-ballActor, actor.world.ball.particleVelocity / ballSpeedLength);

            //方向相反
            if (dot <= Fix64.Zero)
            {
                //Debuger.Log("Negative Direction to getBall" + (float)ballActor.length);
                return(false);
            }

            Fix64 d2 = ballActor.squareLength - dot.square;

            //无交点
            if (d2 > actor.configuration.scb_maxRadius)
            {
                //Debuger.Log("no intersect point" + (float)ballActor.length);
                return(false);
            }


            Fix64 b2 = actor.configuration.scb_maxRadius.square - d2;

            if (b2 <= Fix64.Zero)
            {
                //Debuger.Log("D1");
                return(false);
            }

            Fix64 s = dot - Fix64.Sqrt(b2);

            if (s < Fix64.Zero)
            {
                //Debuger.Log("Ball in Range???" + (float)ballActor.length);
                return(false);
            }

            FixVector2 normalizedBallActor = ballActor.normalized;

            FixVector2 bIntersectPoint = actor.world.ball.getPosition() + s * actor.world.ball.particleVelocity.normalized;

#if UNITY_EDITOR
            LogicEvent.fire("setIntersectPoint", bIntersectPoint);
#endif

            Fix64 t = Fix64.Zero;
            Fix64 dampingAcceleration = Fix64.Zero;
            bool  canReachPoint       = actor.world.ball.estimate(bIntersectPoint, out t, out dampingAcceleration);
            if (!canReachPoint)
            {
                //Debuger.Log("Can not read Point");
                return(false);
            }

            if (t >= actor.configuration.scb_maxCathingTime)
            {
                //Debuger.Log("t > scb_maxCathingTime distance:" + (float)ballActor.length);
                return(false);
            }
            //弹跳次数>1不处理
            EstimateHeightInfo heightInfo = actor.world.ball.estimateHeight(t);
            if (heightInfo.landedTimes > 0)
            {
                //Debuger.Log("heightInfo.landedTimes > 0");
                return(false);
            }

            //脚下停球
            if (heightInfo.destHeight <= actor.configuration.scb_catchingHeightLimit[0])
            {
                ////动画时间太短
                //if (t < actor.configuration.scb_catchingAniTime[0])
                //{
                //    Debuger.Log("t < actor.configuration.scb_catchingAniTime :t=" + (float)t);
                //    return false;
                //}

                //Debuger.Log("StandCatchingBall begin");

                FixVector2 faceTo = (bIntersectPoint - actor.getPosition()).normalized;

                FixVector2 target = actor.getPosition() + faceTo * actor.configuration.scb_catchingOffset[0];

                actor.world.ball.willCatchFreeBall(actor, target, t, actor.configuration.scb_catchingOffsetH[0], Fix64.FastAbs(dampingAcceleration));
                actor.m_stateVector = faceTo;
                actor.m_stateValue  = t;
                actor.m_nextState   = StandCatchingBall.instance;


                return(true);
            }

            for (int i = 1; i < actor.configuration.scb_catchingHeightLimit.Length; ++i)
            {
                if (heightInfo.destHeight > actor.configuration.scb_catchingHeightLimit[i - 1] &&
                    heightInfo.destHeight <= actor.configuration.scb_catchingHeightLimit[i]
                    )
                {
                    //if (t < actor.configuration.scb_catchingAniTime[i])
                    //{
                    //    Debuger.Log("Air Cathing ball can not procced moveTime:t" + (float)t + " aniTime:" + (float)actor.configuration.scb_catchingAniTime[i]);
                    //    return false;
                    //}

                    FixVector2 cPoint = actor.getPosition() + actor.configuration.scb_catchingOffset[i] * ballActor.normalized;

                    actor.world.ball.willCatchFreeBall(actor, cPoint, t, actor.configuration.scb_catchingOffsetH[i], Fix64.FastAbs(dampingAcceleration));
                    actor.m_stateVector    = normalizedBallActor;
                    actor.m_stateValue     = t;
                    actor.m_stateDataIndex = i;
                    actor.m_nextState      = AirCatchingBall.instance;

                    return(true);
                }
            }

            //Debuger.Log("can not get ball heightInfo.destHeight" + (float)heightInfo.destHeight);
            return(false);
        }
Esempio n. 2
0
    void doorKeeperCathingBall(FBActor shooter, FBActor actor)
    {
        //球的轨迹和守门员的交点
        FixVector2 intersectPoint  = FixVector2.kZero;
        Fix64      intersectHeight = Fix64.One;
        Fix64      ballFlyTime     = Fix64.Zero;

        bool canHit = ball.estimateHit(actor.direction, -FixVector2.dot(actor.getPosition(), actor.direction), out ballFlyTime, out intersectPoint, out intersectHeight);

        if (!canHit)
        {
            Debuger.Log("Can not fly to doorkeeper");
            return;
        }

#if UNITY_EDITOR
        LogicEvent.fire("onDoorKeeperCatchingBallView", actor, intersectPoint, intersectHeight);
#endif

        FixVector2 toward           = intersectPoint - actor.getPosition();
        Fix64      distance         = toward.length;
        int        cathingZoneIndex = -1;
        if (distance < actor.configuration.dkcb_edgeLimit[0])
        {
            if (intersectHeight < actor.configuration.dkcb_edgeLimit[1])
            {
                //a区
                cathingZoneIndex = 0;
            }
            else if (intersectHeight < actor.configuration.dkcb_edgeLimit[2])
            {
                //b区
                cathingZoneIndex = 1;
            }
            else if (intersectHeight < actor.configuration.dkcb_edgeLimit[3])
            {
                //c区
                cathingZoneIndex = 2;
            }
            else
            {
                //H区,直接返回,不处理
                cathingZoneIndex = -1;
            }
        }
        else if (distance < actor.configuration.dkcb_edgeLimit[6])
        {
            if (intersectHeight < actor.configuration.dkcb_edgeLimit[4])
            {
                //fe区
                cathingZoneIndex = 4;
            }
            else if (intersectHeight < actor.configuration.dkcb_edgeLimit[5])
            {
                //gd区
                cathingZoneIndex = 3;
            }
            else
            {
                cathingZoneIndex = -1;
            }
        }
        else
        {
            //H区,直接返回,不处理
            cathingZoneIndex = -1;
        }

        bool pretendCatchingBall = false;

        if ((cathingZoneIndex == 3 || cathingZoneIndex == 4))
        {
            //修改获取球的区域
            Fix64      rightDoorV   = shooter.team == FBTeam.kBlue ? new Fix64(1) : new Fix64(-1);
            FixVector2 doorPosition = new FixVector2(config.worldSize.x * rightDoorV, Fix64.Zero);
            Fix64      s            = (shooter.getPosition() - doorPosition).length;
            if (s > shooter.configuration.maxGoalDistance)
            {
                s = shooter.configuration.maxGoalDistance;
            }

            Fix64 shootRate = ConstTable.ShootBall_GoalRate[(int)shooter.shootingType]
                              * ball.getEnergy().goalRate
                              *((Fix64)1.0f - s / shooter.configuration.maxGoalDistance);
            //失误计算
            Fix64 randV = this.randomUnit;
            pretendCatchingBall = randV >= shootRate;

            Debuger.Log("ShootBall GoalRate:" + (float)shootRate + " random:" + (float)randV);

            if (pretendCatchingBall)
            {
                if (cathingZoneIndex == 3)
                {
                    intersectHeight -= ConstTable.GoallKeeperPretendGetBallMissDistance;
                    if (intersectHeight < actor.configuration.dkcb_edgeLimit[4])
                    {
                        cathingZoneIndex = 4;
                    }
                }
                if (cathingZoneIndex == 4)
                {
                    intersectHeight += ConstTable.GoallKeeperPretendGetBallMissDistance;
                    if (intersectHeight > actor.configuration.dkcb_edgeLimit[4])
                    {
                        cathingZoneIndex = 3;
                    }
                }
            }
        }


        if (cathingZoneIndex != -1)
        {
            actor.doCathingGoalBall(new FixVector2(intersectPoint.x, intersectPoint.y), intersectHeight, ballFlyTime, cathingZoneIndex, pretendCatchingBall);
        }
    }
Esempio n. 3
0
    public FBActor findTarget(FBActor src, FixVector2 direction, int index, int teamMask, FBActor exclude)
    {
        Fix64 maxRadius  = src.configuration.passBallMaxR[index];
        Fix64 minRadius  = src.configuration.passBallMinR[index];
        Fix64 theta      = src.configuration.passBallFov[index];
        Fix64 bestRadius = m_ball.owner.configuration.passBallBestR[index];

        if (theta <= Fix64.Zero)
        {
            return(null);
        }

        var cosTheta = Fix64.Cos(theta);

        List <FBActor> preferTargets = new List <FBActor>();
        var            actorCount    = m_actors.Count;

        for (int i = 0; i < actorCount; i++)
        {
            var actor = m_actors[i];
            if (actor == exclude || ((int)actor.team & teamMask) == 0)
            {
                continue;
            }
            var d   = actor.particle.position - src.getPosition();
            var len = d.length;
            if (len < minRadius || len > maxRadius)
            {
                continue;
            }
            var cos = Fix64.Zero;
            if (len == Fix64.Zero)
            {
                cos = Fix64.One;
            }
            else
            {
                cos = FixVector2.dot(d.normalized, direction);
            }
            if (cos < cosTheta)
            {
                continue;
            }

            preferTargets.Add(actor);
        }

        FixVector2 preferPoint = src.getPosition() + direction * bestRadius;

        preferTargets.Sort(new FBActorTargetFindCompare(preferPoint));


        FBActor destTarget = null;

        for (int i = 0; i < preferTargets.Count; ++i)
        {
            if (checkBlocked(src, preferTargets[i]))
            {
                continue;
            }
            destTarget = preferTargets[i];
            break;
        }

#if UNITY_EDITOR
        LogicEvent.fire("onMainCharacterPassingBall", src, direction, index, destTarget, preferTargets);
#endif

        return(destTarget);
    }
Esempio n. 4
0
    public void endSample()
    {
        FixVector2 curPosition = getPosition();
        var        length      = (curPosition - lastPosition).squareLength;
        var        heightDelta = Fix64.Abs(height - lastHeight);

        if (forceCheck || length > (Fix64)0.0001f || height > Fix64.Zero)
        {
            if (height > Fix64.Zero)
            {
                world.fbGame.generateRenderAction <RAL.ActorMovingAction3D>(id, new FixVector3(curPosition.x, height, curPosition.y).toVector3(), ignorePositionSampleSlerp, (uint)defendMoveDirection);
            }
            else
            {
                world.fbGame.generateRenderAction <RAL.ActorMovingAction>(id, new FixVector2(curPosition.x, curPosition.y).toVector2(), ignorePositionSampleSlerp, (uint)defendMoveDirection);
            }
            if (endMove)
            {
                endMove = false;
            }
        }
        else
        {
            if (!endMove)
            {
                world.fbGame.generateRenderAction <RAL.ActorEndMoveAction>(id);
                endMove = true;
            }
        }

        if (checkMovingState() &&
            particle.velocity != FixVector2.kZero &&
            length <= (Fix64)1e-3)
        {
            world.fbGame.generateRenderAction <RAL.ChangeActorAnimatorSpeedAction>(id, (float)calculateAnimatorSpeedOfRun(0));
        }
        if (ignorePositionSampleSlerp)
        {
            ignorePositionSampleSlerp = false;
        }

        bool sampleDirection = forceCheck || (!ignoreDirectionSample && FixVector2.dot(direction, lastDirection) < Fix64.One && direction != FixVector2.kZero);

        if (sampleDirection)
        {
            world.fbGame.generateRenderAction <RAL.TurningAction>(this.id, lastDirection.toVector2(), direction.toVector2(), ignoreDirectionSlerp);
        }

        if (ignoreDirectionSample)
        {
            ignoreDirectionSample = false;
        }
        if (ignoreDirectionSlerp)
        {
            ignoreDirectionSlerp = false;
        }

        if (forceCheck)
        {
            forceCheck = false;
        }
    }