示例#1
0
        public ICommandResult Simulate(ICommandInput commandInput, Unit unit)
        {
            CommandInput_Move input_Move        = commandInput as CommandInput_Move;
            UnitPathComponent unitPathComponent = unit.GetComponent <UnitPathComponent>();

            PathfindingComponent pathfindingComponent = Game.Scene.GetComponent <PathfindingComponent>();

            unitPathComponent.ABPath = ComponentFactory.Create <ABPathWrap, Vector3, Vector3>(unit.Position, input_Move.clickPos);
            pathfindingComponent.Search(unitPathComponent.ABPath);

            CommandResult_Move result_Move = CommandGCHelper.GetCommandResult <CommandResult_Move>();

            result_Move.Path = unitPathComponent.ABPath.Result;
            // result_Move.dir = input_Move.moveDir;// 暂时就以输入的方向作为角色的方向
            return(result_Move);
        }
        //从哪一帧开始重新计算
        public void ReCal(int startFrame)
        {
            for (int i = simulateFrame; i >= startFrame; i--)
            {
                if (cacheCommands.ContainsKey(i))
                {
                    foreach (var v in cacheCommands[i])
                    {
                        switch (v.commandInput)
                        {
                        //移动的话,直接取最后一次的目标作为目标就好了.
                        case CommandInput_Move input_Move:

                            CommandResult_Move result_Move = simulaterComponent.commandSimulaters[input_Move.GetType()].Simulate(input_Move, unit) as CommandResult_Move;
                            v.commandResult = result_Move;
                            //直接拉扯
                            unit.GetComponent <CharacterMoveComponent>().MoveAsync(result_Move.Path).Coroutine();
                            break;
                        }
                        return;
                    }
                }
            }
        }
        public void FixedUpdate()
        {
            //TODO; 和上一次服务器确认帧相差多少之后,提示网络有问题
            simulateFrame++;
            //先上传这一帧的操作,同时缓存操作,然后客户端自己模拟操作的结果
            if (collectedNewInput)
            {
                collectedNewInput            = false;
                cacheCommands[simulateFrame] = new List <Command>();
                cacheCommands[simulateFrame].AddRange(currCommands.Values);
                currCommands.Clear();
                foreach (var v in cacheCommands[simulateFrame])
                {
                    switch (v.commandInput)
                    {
                    case CommandInput_Move input_Move:



                        CommandResult_Move result_Move = simulaterComponent.commandSimulaters[input_Move.GetType()].Simulate(input_Move, unit) as CommandResult_Move;
                        v.commandResult = result_Move;

                        //再预测这一帧的结果
                        unit.GetComponent <CharacterMoveComponent>().MoveAsync(result_Move.Path).Coroutine();

                        //单机模式不发送网络消息
                        if (!Game.Scene.GetComponent <GlobalConfigComponent>().networkPlayMode)
                        {
                            break;
                        }
                        Log.Debug("frame : " + simulateFrame + "  本地预测的路径: " + result_Move.Path.ListToString <Vector3>());
                        inputInfo_Move.Frame  = simulateFrame;
                        inputInfo_Move.AimPos = input_Move.clickPos.ToV3Info();
                        ETModel.Game.Scene.GetComponent <SessionComponent>().Session.Send(inputInfo_Move);

                        break;

                    case CommandInput_UseSkill input_UseSkill:

                        CommandResult_UseSkill result_UseSkill = simulaterComponent.commandSimulaters[input_UseSkill.GetType()].Simulate(input_UseSkill, unit) as CommandResult_UseSkill;
                        v.commandResult = result_UseSkill;

                        if (!Game.Scene.GetComponent <GlobalConfigComponent>().networkPlayMode)
                        {
                            //单机的话本地直接做决定了
                            unit.GetComponent <ActiveSkillComponent>().tcs?.SetResult(result_UseSkill.success);
                            break;
                        }

                        switch (input_UseSkill.bufferValue)
                        {
                        case BufferValue_Pos value_Pos:
                            Input_UseSkill_Pos.Frame          = simulateFrame;
                            Input_UseSkill_Pos.SkillId        = input_UseSkill.skillId;
                            Input_UseSkill_Pos.PipelineSignal = input_UseSkill.pipelineSignal;

                            Input_UseSkill_Pos.AimPos = value_Pos.aimPos.ToV3Info();
                            ETModel.Game.Scene.GetComponent <SessionComponent>().Session.Send(Input_UseSkill_Pos);
                            break;

                        case BufferValue_Dir value_Dir:
                            Input_UseSkill_Dir.Frame          = simulateFrame;
                            Input_UseSkill_Dir.SkillId        = input_UseSkill.skillId;
                            Input_UseSkill_Dir.PipelineSignal = input_UseSkill.pipelineSignal;

                            Input_UseSkill_Dir.AimDir = value_Dir.dir.ToV3Info();
                            ETModel.Game.Scene.GetComponent <SessionComponent>().Session.Send(Input_UseSkill_Dir);
                            break;

                        case BufferValue_TargetUnits value_TargetUnits:
                            Input_UseSkill_Tar.Frame          = simulateFrame;
                            Input_UseSkill_Tar.SkillId        = input_UseSkill.skillId;
                            Input_UseSkill_Tar.PipelineSignal = input_UseSkill.pipelineSignal;

                            Input_UseSkill_Tar.UnitId = value_TargetUnits.targets[0].Id;
                            ETModel.Game.Scene.GetComponent <SessionComponent>().Session.Send(Input_UseSkill_Tar);
                            break;

                        default:
                            break;
                        }

                        break;
                    }
                }
            }
        }