692 lines
34 KiB
C#
692 lines
34 KiB
C#
/*
|
||
* @Author: 白哉
|
||
* @Description: 行为逻辑类
|
||
* @Date: 2025年04月10日 星期四 11:04:44
|
||
* @Modify:
|
||
*/
|
||
|
||
|
||
using System;
|
||
using System.Collections.Generic;
|
||
using System.Linq;
|
||
using Logic.AI;
|
||
using Logic.CrashSight;
|
||
using RuntimeData;
|
||
using TH1_Logic.Core;
|
||
using UnityEngine;
|
||
using TH1Renderer;
|
||
using TH1Resource;
|
||
using UnityEditor;
|
||
using UnityEngineInternal;
|
||
|
||
|
||
//这里是所有BuildAction派生子类的实现模块
|
||
namespace Logic.Action
|
||
{
|
||
|
||
|
||
// TrainUnit 训练单位类
|
||
public class TrainUnitAction : ActionLogicBase
|
||
{
|
||
public TrainUnitAction(CommonActionId id) : base(id)
|
||
{
|
||
|
||
}
|
||
|
||
|
||
protected bool TrainUnitActionCheckBaseData(CommonActionParams actionParam)
|
||
{
|
||
if (actionParam.PlayerData == null) return false;
|
||
return true;
|
||
}
|
||
protected bool TrainUnitActionCheckHasTech(CommonActionParams actionParam)
|
||
{
|
||
//如果没科技,return
|
||
if(!actionParam.PlayerData.TechTree.CheckActionCan(_actionId))
|
||
return false;
|
||
return true;
|
||
}
|
||
|
||
protected bool TrainUnitActionCheckWaterUnit()
|
||
{
|
||
if (Table.Instance.UnitTypeDataAssets.GetUnitTypeInfo(_actionId.UnitType,_actionId.GiantType,_actionId.UnitLevel,out var info)
|
||
&& info.LandType == LandType.WaterAndAshore)
|
||
return true;
|
||
return false;
|
||
}
|
||
|
||
protected bool TrainUnitActionCheckCityFullPop(CommonActionParams actionParam)
|
||
{
|
||
if (actionParam.MainObjectType == MainObjectType.City)
|
||
{
|
||
if (actionParam.MapData.CheckIfCityFullPopulation(actionParam.CityData)) return true;
|
||
}
|
||
|
||
if (actionParam.MainObjectType == MainObjectType.Grid)
|
||
{
|
||
if (!actionParam.MapData.GetCityDataByTerritoryGid(actionParam.GridData.Id, out var city)) return true;
|
||
if (actionParam.MapData.CheckIfCityFullPopulation(city)) return true;
|
||
}
|
||
return false;
|
||
}
|
||
|
||
protected bool TrainUnitActionCheckCityBelongPlayer(CommonActionParams actionParam)
|
||
{
|
||
if (actionParam.PlayerData == null) return false;
|
||
if (!actionParam.MapData.GetPlayerDataByCityId(actionParam.CityData.Id, out var playerData)
|
||
|| playerData.Id != actionParam.PlayerData.Id)
|
||
return false;
|
||
return true;
|
||
}
|
||
|
||
protected bool TrainUnitActionCheckGridBelongPlayer(CommonActionParams actionParam)
|
||
{
|
||
if (actionParam.GridData == null ||
|
||
!actionParam.MapData.GetPlayerDataByTerritoryGridId(actionParam.GridData.Id, out var player))
|
||
return false;
|
||
if (player.Id != actionParam.PlayerData.Id)
|
||
return false;
|
||
return true;
|
||
}
|
||
|
||
protected bool TrainUnitActionCheckUnitOnCity(CommonActionParams actionParam)
|
||
{
|
||
if (!actionParam.MapData.GetGridDataByCityId(actionParam.CityData?.Id ?? 0, out var grid)) return true;
|
||
if (actionParam.MapData.GetUnitDataByGid(grid.Id, out var unitData)) return true;
|
||
return false;
|
||
}
|
||
|
||
protected bool TrainUnitActionCheckEnemyUnitOnGrid(CommonActionParams actionParam)
|
||
{
|
||
if (actionParam.MapData.GetUnitDataByGid(actionParam.GridData.Id, out var unitData)
|
||
&& actionParam.MapData.GetPlayerDataByUnitId(unitData.Id,out var unitPlayer)
|
||
&& !actionParam.MapData.SameUnion(unitPlayer.Id,actionParam.PlayerId)) return true;
|
||
return false;
|
||
}
|
||
|
||
protected bool TrainUnitActionCheckUnitOnGrid(CommonActionParams actionParam)
|
||
{
|
||
if (actionParam.MapData.GetUnitDataByGid(actionParam.GridData.Id, out var unitData)) return true;
|
||
return false;
|
||
}
|
||
|
||
protected bool TrainUnitActionCheckMoneyEnough(CommonActionParams actionParam)
|
||
{
|
||
if (GetCost() > actionParam.PlayerData.PlayerCoin) return false;
|
||
return true;
|
||
}
|
||
|
||
protected override bool Execute(CommonActionParams actionParams)
|
||
{
|
||
if (_actionId.UnitType == UnitType.None)
|
||
return false;
|
||
if (actionParams.MainObjectType == MainObjectType.City && actionParams.CityData == null)
|
||
return false;
|
||
if (actionParams.MainObjectType == MainObjectType.Grid && actionParams.GridData == null)
|
||
return false;
|
||
|
||
if (!CheckCan(actionParams)) return false;
|
||
|
||
GridData gridData = null;
|
||
CityData cityData = null;
|
||
|
||
|
||
//如果是city产兵
|
||
if (actionParams.MainObjectType == MainObjectType.City)
|
||
{
|
||
cityData = actionParams.CityData;
|
||
//从city处获得准确的gridData
|
||
if (!actionParams.MapData.GetGridDataByCityId(actionParams.CityData.Id, out gridData))
|
||
return false;
|
||
}
|
||
|
||
//否则如果是grid产兵
|
||
if (actionParams.MainObjectType == MainObjectType.Grid)
|
||
{
|
||
//从actionParams获得准确的gridData
|
||
gridData = actionParams.GridData;
|
||
if (actionParams.CityData != null)
|
||
cityData = actionParams.CityData;
|
||
else
|
||
actionParams.MapData.GetCityDataByTerritoryGid(gridData.Id, out cityData);
|
||
|
||
}
|
||
|
||
if (gridData == null)
|
||
return false;
|
||
|
||
//减去花费
|
||
actionParams.PlayerData.SpendCoin(GetCost());
|
||
|
||
//生产新单位
|
||
if(!actionParams.MapData.AddUnitData(gridData.Id,cityData.Id,new UnitFullType(_actionId.UnitType,_actionId.GiantType,0),out var newUnit))
|
||
return false;
|
||
|
||
//Step #4 如果是天狗酒馆,每回合首个生产的单位可以立刻行动,天狗骑兵获得天狗之风
|
||
if(actionParams.GridData is { Resource: ResourceType.MoriyaMilitary, NavalBasePoint: > 0 })
|
||
{
|
||
actionParams.GridData.NavalBasePoint = 0;
|
||
newUnit.SetFullAPCPMP();
|
||
//TODO 这里是hard code
|
||
if(newUnit.UnitType == UnitType.MoriyaRider)
|
||
newUnit.AddSkill(SkillType.SNEAK,actionParams.MapData,newUnit.Id);
|
||
//判断是否要更新视觉
|
||
if (newUnit.InMainSight())
|
||
newUnit.Renderer(actionParams.MapData)?.RenderUpdateUnitGlow();
|
||
}
|
||
|
||
cityData.SetCityRenderer(actionParams.MapData);
|
||
//更新视野
|
||
var count = Main.PlayerLogic.UpdateSight_LogicView(actionParams.MapData,actionParams.PlayerData,actionParams.MapData.GridMap.GetAroundGridIdList(newUnit.GetSightRange(actionParams.MapData),gridData));
|
||
newUnit.HeroTask(actionParams.MapData)?.OnExploredGrids(actionParams.MapData, newUnit, count);
|
||
foreach (var kv in actionParams.PlayerData.PlayerHeroData.HeroTaskDict) kv.Value.OnAnyExploredGrids(actionParams.MapData, newUnit, count);
|
||
//如果是真mapdata,增加得分,然后处理得分动画
|
||
if (Main.MapData == actionParams.MapData)// && actionParams.PlayerData.Id == actionParams.MapData.PlayerMap.SelfPlayerData.Id)
|
||
{
|
||
var v1 = Table.Instance.GridToWorld(gridData);
|
||
int score = GetCost() * 5;
|
||
if (actionParams.PlayerData.Id == actionParams.MapData.PlayerMap.SelfPlayerData.Id)
|
||
{
|
||
MapRenderer.Instance.ProjectileManager.CreateProjectileFaith(v1,score);
|
||
}
|
||
AchievementDataManager.Instance.OnTrainUnit(actionParams.MapData, actionParams.PlayerData, actionParams.CityData, newUnit);
|
||
}
|
||
return true;
|
||
}
|
||
|
||
public override bool CheckCan(CommonActionParams actionParam)
|
||
{
|
||
GridData gridData;
|
||
PlayerData playerData;
|
||
CityData cityData;
|
||
|
||
//step #0 基础鲁棒性 (playerData不能为空)
|
||
if (!TrainUnitActionCheckBaseData(actionParam)) return false;
|
||
|
||
//Part1 如果是城市产兵
|
||
if (actionParam.MainObjectType == MainObjectType.City)
|
||
{
|
||
|
||
//step #1 city产兵的特殊鲁棒性
|
||
if (actionParam.CityData == null) return false;
|
||
//step #2 check player操作的city 是不是自己的city,存储gridData
|
||
if (!TrainUnitActionCheckCityBelongPlayer(actionParam)) return false;
|
||
//step #3 赋值gridData(city的位置)
|
||
if (!actionParam.MapData.GetGridDataByCityId(actionParam.CityData.Id, out gridData)) return false;
|
||
//step #4如果没科技,return
|
||
if(!TrainUnitActionCheckHasTech(actionParam)) return false;
|
||
//step #5确认是否是水生unit
|
||
if (TrainUnitActionCheckWaterUnit()) return false;
|
||
//step #6 确认城市是否满员
|
||
if (TrainUnitActionCheckCityFullPop(actionParam)) return false;
|
||
//step #7 如果城市上面有单位,不能生产,不显示
|
||
if (TrainUnitActionCheckUnitOnCity(actionParam)) return false;
|
||
//step #8 判断钱够不够
|
||
if (!TrainUnitActionCheckMoneyEnough(actionParam)) return false;
|
||
//step #9 只处理非英雄
|
||
if (_actionId.UnitType == UnitType.Giant) return false;
|
||
return true;
|
||
}
|
||
//Part2 如果是grid产兵
|
||
if (actionParam.MainObjectType == MainObjectType.Grid)
|
||
{
|
||
//step #1 确认基础鲁棒性
|
||
if (actionParam.GridData == null) return false;
|
||
gridData = actionParam.GridData;
|
||
//step #2 进行基础赋值
|
||
if (!actionParam.MapData.GetCityDataByTerritoryGid(gridData.Id, out cityData)) return false;
|
||
if (!actionParam.MapData.GetPlayerDataByCityId(cityData.Id, out playerData)) return false;
|
||
//step #3 check city是不是player的
|
||
if (!TrainUnitActionCheckGridBelongPlayer(actionParam)) return false;
|
||
//step #4 如果没科技,return
|
||
if (!TrainUnitActionCheckHasTech(actionParam)) return false;
|
||
//step #5 如果城市满员
|
||
if (TrainUnitActionCheckCityFullPop(actionParam)) return false;
|
||
//step #6如果格子上面有单位,不能生产,不显示
|
||
if (TrainUnitActionCheckUnitOnGrid(actionParam)) return false;
|
||
//step #7判断钱够不够
|
||
if (!TrainUnitActionCheckMoneyEnough(actionParam)) return false;
|
||
//step #8 只处理非英雄
|
||
if (_actionId.UnitType == UnitType.Giant) return false;
|
||
|
||
//----------终于进入正式的特判环节,前面都是通用判断,下面开始进入白名单
|
||
|
||
//Part 2.2
|
||
//军营产兵
|
||
if (gridData.Resource == ResourceType.Military ||gridData.Resource == ResourceType.RemiliaMilitary || gridData.Resource == ResourceType.MoriyaMilitary)
|
||
{
|
||
//step #1 如果水生unit,不行
|
||
if(TrainUnitActionCheckWaterUnit()) return false;
|
||
//step #2 如果是伟人,return
|
||
if (_actionId.UnitType == UnitType.Giant) return false;
|
||
return true;
|
||
}
|
||
|
||
}
|
||
return false;
|
||
|
||
}
|
||
public override bool CheckShow(CommonActionParams actionParam,out ShowType showType)
|
||
{
|
||
showType = ShowType.None;
|
||
GridData gridData;
|
||
PlayerData playerData;
|
||
CityData cityData;
|
||
|
||
//step #0 基础鲁棒性 (playerData不能为空)
|
||
if (!TrainUnitActionCheckBaseData(actionParam)) return false;
|
||
|
||
//Part1 如果是城市产兵
|
||
if (actionParam.MainObjectType == MainObjectType.City)
|
||
{
|
||
|
||
//step #1 city产兵的特殊鲁棒性
|
||
if (actionParam.CityData == null) return false;
|
||
//step #2 check player操作的city 是不是自己的city,存储gridData
|
||
if (!TrainUnitActionCheckCityBelongPlayer(actionParam)) return false;
|
||
//step #3 赋值gridData(city的位置)
|
||
if (!actionParam.MapData.GetGridDataByCityId(actionParam.CityData.Id, out gridData)) return false;
|
||
//step #4如果没科技,return
|
||
if(!TrainUnitActionCheckHasTech(actionParam)) return false;
|
||
//step #5确认是否是水生unit
|
||
if (TrainUnitActionCheckWaterUnit()) return false;
|
||
//step #8 判断钱够不够
|
||
if (!TrainUnitActionCheckMoneyEnough(actionParam)) showType = ShowType.Cost;
|
||
//step #6 确认城市是否满员
|
||
if (TrainUnitActionCheckCityFullPop(actionParam)) showType = ShowType.Locked;
|
||
//step #7 如果城市上面有单位,不能生产,不显示
|
||
if (TrainUnitActionCheckUnitOnCity(actionParam)) return false;
|
||
|
||
//step #9 只处理非英雄
|
||
if (_actionId.UnitType == UnitType.Giant) return false;
|
||
return true;
|
||
}
|
||
//Part2 如果是grid产兵
|
||
if (actionParam.MainObjectType == MainObjectType.Grid)
|
||
{
|
||
//step #1 确认基础鲁棒性
|
||
if (actionParam.GridData == null) return false;
|
||
gridData = actionParam.GridData;
|
||
//step #2 进行基础赋值
|
||
if (!actionParam.MapData.GetCityDataByTerritoryGid(gridData.Id, out cityData)) return false;
|
||
if (!actionParam.MapData.GetPlayerDataByCityId(cityData.Id, out playerData)) return false;
|
||
//step #3 check city是不是player的
|
||
if (!TrainUnitActionCheckGridBelongPlayer(actionParam)) return false;
|
||
//step #4 如果没科技,return
|
||
if (!TrainUnitActionCheckHasTech(actionParam)) return false;
|
||
//step #7判断钱够不够
|
||
if (!TrainUnitActionCheckMoneyEnough(actionParam)) showType = ShowType.Cost;
|
||
//step #5 如果城市满员
|
||
if (TrainUnitActionCheckCityFullPop(actionParam)) showType = ShowType.Locked;
|
||
//step #6如果格子上面有单位,不能生产,不显示
|
||
if (TrainUnitActionCheckUnitOnGrid(actionParam)) return false;
|
||
|
||
//step #8 只处理非英雄
|
||
if (_actionId.UnitType == UnitType.Giant) return false;
|
||
|
||
//----------终于进入正式的特判环节,前面都是通用判断,下面开始进入白名单
|
||
//Part 2.2
|
||
//军营产兵
|
||
if (gridData.Resource == ResourceType.Military ||gridData.Resource == ResourceType.RemiliaMilitary || gridData.Resource == ResourceType.MoriyaMilitary)
|
||
{
|
||
//step #1 如果水生unit,不行
|
||
if(TrainUnitActionCheckWaterUnit()) return false;
|
||
//step #2 如果是伟人,return
|
||
if (_actionId.UnitType == UnitType.Giant) return false;
|
||
return true;
|
||
}
|
||
|
||
}
|
||
return false;
|
||
|
||
|
||
}
|
||
public override ActionShowState CheckShowState(CommonActionParams actionParams) { return ActionShowState.None; }
|
||
}
|
||
|
||
public class TrainUnitActionTrainHero : TrainUnitAction
|
||
{
|
||
private GridData _finalGrid;
|
||
private CityData _finalCity;
|
||
private UnitData _newUnit;
|
||
|
||
public TrainUnitActionTrainHero(CommonActionId id) : base(id){}
|
||
|
||
//确认英雄的冷却cd
|
||
private bool CheckGiantHasColdTime(CommonActionParams actionParam)
|
||
{
|
||
if (actionParam.PlayerData == null) return true;
|
||
if (!Table.Instance.UnitTypeDataAssets.GetUnitTypeInfo(UnitType.Giant, _actionId.GiantType, 0,
|
||
out var info)) return true;
|
||
if (actionParam.PlayerData.giantPenalty[(uint)info.ChessType] > 0) return true;
|
||
return false;
|
||
}
|
||
|
||
//判断场上的giant是否已经有一个了(会处理芙兰这种quartet的情况)
|
||
|
||
private bool CheckHeroHasOne(CommonActionParams actionParam)
|
||
{
|
||
uint heroLevel = _actionId.UnitLevel;
|
||
heroLevel = actionParam.PlayerData.PlayerHeroData.GetHeroLevel(_actionId.GiantType);
|
||
//获取unitTypeInfo,level=0时的信息
|
||
if(!Table.Instance.UnitTypeDataAssets.GetUnitTypeInfo(_actionId.UnitType, _actionId.GiantType,heroLevel,
|
||
out var heroInfo))
|
||
return true;
|
||
//如果有Unique且全场已经有1个了
|
||
if (heroInfo.Skills.Contains(SkillType.UNIQUE))
|
||
{
|
||
if (Main.PlayerLogic.GetMapUnitTypeCount(actionParam.MapData, _actionId.UnitType, _actionId.GiantType) > 0) return true;
|
||
//额外处理妹红的蛋
|
||
if(_actionId.GiantType == GiantType.FrenchMokou &&
|
||
(Main.PlayerLogic.GetMapUnitTypeCount(actionParam.MapData, UnitType.KaguyaFrenchMokouEgg, GiantType.None) > 0))
|
||
return true;
|
||
}
|
||
//如果有DUO且全场已经有2个了
|
||
if (heroInfo.Skills.Contains(SkillType.DUO))
|
||
{
|
||
if(Main.PlayerLogic.GetMapUnitTypeCount(actionParam.MapData,_actionId.UnitType, _actionId.GiantType) > 1)
|
||
return true;
|
||
}
|
||
//如果有TRIO且全场已经有3个了
|
||
if (heroInfo.Skills.Contains(SkillType.TRIO))
|
||
{
|
||
if(Main.PlayerLogic.GetMapUnitTypeCount(actionParam.MapData,_actionId.UnitType, _actionId.GiantType) > 2)
|
||
return true;
|
||
}
|
||
//如果有QUARTER且全场已经有4个了
|
||
if (heroInfo.Skills.Contains(SkillType.QUARTET))
|
||
{
|
||
if(Main.PlayerLogic.GetMapUnitTypeCount(actionParam.MapData,_actionId.UnitType, _actionId.GiantType) > 3)
|
||
return true;
|
||
}
|
||
|
||
return false;
|
||
}
|
||
protected override bool Execute(CommonActionParams actionParams)
|
||
{
|
||
//step #0 鲁棒性检查
|
||
if (!CheckCan(actionParams)) return false;
|
||
//step #1 获得准确的gridData和对应的cityData
|
||
//step #1 part1 如果是city产英雄
|
||
if (actionParams.MainObjectType == MainObjectType.City)
|
||
{
|
||
_finalCity = actionParams.CityData;
|
||
//从city处获得准确的gridData
|
||
if (!actionParams.MapData.GetGridDataByCityId(actionParams.CityData.Id, out _finalGrid))
|
||
return false;
|
||
}
|
||
//step #1 part2 否则如果是grid产英雄
|
||
if (actionParams.MainObjectType == MainObjectType.Grid)
|
||
{
|
||
//从actionParams获得准确的gridData
|
||
_finalGrid = actionParams.GridData;
|
||
if (actionParams.CityData != null)
|
||
_finalCity = actionParams.CityData;
|
||
else
|
||
actionParams.MapData.GetCityDataByTerritoryGid(_finalGrid.Id, out _finalCity);
|
||
}
|
||
if (_finalGrid == null) return false;
|
||
|
||
//step #2 确定giant的真实level
|
||
var realLv = actionParams.PlayerData.PlayerHeroData.GetHeroLevel(_actionId.GiantType);
|
||
//step #3 生产新单位
|
||
if (!actionParams.MapData.AddUnitData(_finalGrid.Id, _finalCity.Id,
|
||
new UnitFullType(_actionId.UnitType, _actionId.GiantType, realLv), out _newUnit))
|
||
return false;
|
||
|
||
//Step #4 如果是天狗酒馆,每回合首个生产的单位可以立刻行动
|
||
if(actionParams.MainObjectType == MainObjectType.Grid && actionParams.GridData.Resource == ResourceType.MoriyaMilitary && actionParams.GridData.NavalBasePoint > 0)
|
||
{
|
||
actionParams.GridData.NavalBasePoint = 0;
|
||
_newUnit.SetFullAPCPMP();
|
||
//判断是否要更新视觉
|
||
//判断是否要更新视觉
|
||
if (_newUnit.InMainSight())
|
||
_newUnit.Renderer(actionParams.MapData)?.RenderUpdateUnitGlow();
|
||
|
||
}
|
||
|
||
//step #5 更新新单位周围的视野
|
||
var count = Main.PlayerLogic.UpdateSight_LogicView(actionParams.MapData,actionParams.PlayerData,actionParams.MapData.GridMap.GetAroundGridIdList(_newUnit.GetSightRange(actionParams.MapData),_finalGrid));
|
||
_newUnit.HeroTask(actionParams.MapData)?.OnExploredGrids(actionParams.MapData, _newUnit, count);
|
||
foreach (var kv in actionParams.PlayerData.PlayerHeroData.HeroTaskDict) kv.Value.OnAnyExploredGrids(actionParams.MapData, _newUnit, count);
|
||
ExecuteViewAfter(actionParams);
|
||
return true;
|
||
}
|
||
|
||
public override bool CheckCan(CommonActionParams actionParam)
|
||
{
|
||
//step #0 基础鲁棒性 (playerData不能为空 不是英雄则直接排除
|
||
if(_actionId.UnitType != UnitType.Giant) return false;
|
||
|
||
if (!TrainUnitActionCheckBaseData(actionParam)) return false;
|
||
|
||
GridData gridData;
|
||
PlayerData playerData;
|
||
CityData cityData;
|
||
|
||
//Part1 如果是城市产英雄
|
||
if (actionParam.MainObjectType == MainObjectType.City)
|
||
{
|
||
|
||
//step #1 city产兵的特殊鲁棒性
|
||
if (actionParam.CityData == null) return false;
|
||
//step #2 check player操作的city 是不是自己的city,存储gridData
|
||
if (!TrainUnitActionCheckCityBelongPlayer(actionParam)) return false;
|
||
//step #3 赋值gridData(city的位置)
|
||
if (!actionParam.MapData.GetGridDataByCityId(actionParam.CityData.Id, out gridData)) return false;
|
||
//step #4如果HeroList没有英雄
|
||
if (!actionParam.PlayerData.PlayerHeroData.HasHero(_actionId.GiantType)) return false;
|
||
//step #5 确认城市是否满员
|
||
if (TrainUnitActionCheckCityFullPop(actionParam)) return false;
|
||
//step #6 如果城市上面有单位,不能生产,不显示
|
||
if (TrainUnitActionCheckUnitOnCity(actionParam)) return false;
|
||
//step #7 如果英雄在冷却cd
|
||
if (CheckGiantHasColdTime(actionParam)) return false;
|
||
//step #8 如果英雄违反了UNIQUE或类似的技能如QUARTET
|
||
if (CheckHeroHasOne(actionParam)) return false;
|
||
|
||
return true;
|
||
}
|
||
//Part2 如果是grid产英雄
|
||
if (actionParam.MainObjectType == MainObjectType.Grid)
|
||
{
|
||
//step #1 确认基础鲁棒性
|
||
if (actionParam.GridData == null) return false;
|
||
gridData = actionParam.GridData;
|
||
//step #2 进行基础赋值
|
||
if (!actionParam.MapData.GetCityDataByTerritoryGid(gridData.Id, out cityData)) return false;
|
||
if (!actionParam.MapData.GetPlayerDataByCityId(cityData.Id, out playerData)) return false;
|
||
//step #3 check grid是不是player的
|
||
if (!TrainUnitActionCheckGridBelongPlayer(actionParam)) return false;
|
||
//step #4如果HeroList没有英雄
|
||
if (!actionParam.PlayerData.PlayerHeroData.HasHero(_actionId.GiantType)) return false;
|
||
//step #5 如果城市满员
|
||
if (TrainUnitActionCheckCityFullPop(actionParam)) return false;
|
||
//step #6如果格子上面有单位,不能生产,不显示
|
||
if (TrainUnitActionCheckUnitOnGrid(actionParam)) return false;
|
||
//step #7 如果英雄在冷却cd
|
||
if (CheckGiantHasColdTime(actionParam)) return false;
|
||
//step #8 如果英雄违反了UNIQUE或类似的技能如QUARTET
|
||
if (CheckHeroHasOne(actionParam)) return false;
|
||
|
||
if (_actionId.UnitType == UnitType.Giant
|
||
&& (gridData.Resource is ResourceType.Military or ResourceType.RemiliaMilitary or ResourceType.MoriyaMilitary))
|
||
return true;
|
||
|
||
}
|
||
return false;
|
||
|
||
}
|
||
public override bool CheckShow(CommonActionParams actionParam,out ShowType showType)
|
||
{
|
||
showType = ShowType.None;
|
||
//step #0 基础鲁棒性 (playerData不能为空 不是英雄则直接排除
|
||
if(_actionId.UnitType != UnitType.Giant) return false;
|
||
if (!TrainUnitActionCheckBaseData(actionParam)) return false;
|
||
|
||
GridData gridData;
|
||
PlayerData playerData;
|
||
CityData cityData;
|
||
|
||
|
||
//Part1 如果是城市产英雄
|
||
if (actionParam.MainObjectType == MainObjectType.City)
|
||
{
|
||
|
||
//step #1 city产兵的特殊鲁棒性
|
||
if (actionParam.CityData == null) return false;
|
||
//step #2 check player操作的city 是不是自己的city,存储gridData
|
||
if (!TrainUnitActionCheckCityBelongPlayer(actionParam)) return false;
|
||
//step #3 赋值gridData(city的位置)
|
||
if (!actionParam.MapData.GetGridDataByCityId(actionParam.CityData.Id, out gridData)) return false;
|
||
//step #4如果HeroList没有英雄
|
||
if (!actionParam.PlayerData.PlayerHeroData.HasHero(_actionId.GiantType)) return false;
|
||
//step #5 确认城市是否满员
|
||
if (TrainUnitActionCheckCityFullPop(actionParam)) showType = ShowType.Locked;
|
||
//step #6 如果城市上面有单位,不能生产,不显示
|
||
if (TrainUnitActionCheckUnitOnCity(actionParam)) return false;
|
||
//step #7 如果英雄在冷却cd
|
||
if (CheckGiantHasColdTime(actionParam)) showType = ShowType.Cold;
|
||
//step #8 如果英雄违反了UNIQUE或类似的技能如QUARTET
|
||
if (CheckHeroHasOne(actionParam)) return false;
|
||
|
||
return true;
|
||
}
|
||
//Part2 如果是grid产英雄
|
||
if (actionParam.MainObjectType == MainObjectType.Grid)
|
||
{
|
||
//step #1 确认基础鲁棒性
|
||
if (actionParam.GridData == null) return false;
|
||
gridData = actionParam.GridData;
|
||
//step #2 进行基础赋值
|
||
if (!actionParam.MapData.GetCityDataByTerritoryGid(gridData.Id, out cityData)) return false;
|
||
if (!actionParam.MapData.GetPlayerDataByCityId(cityData.Id, out playerData)) return false;
|
||
//step #3 check grid是不是player的
|
||
if (!TrainUnitActionCheckGridBelongPlayer(actionParam)) return false;
|
||
//step #4如果HeroList没有英雄
|
||
if (!actionParam.PlayerData.PlayerHeroData.HasHero(_actionId.GiantType)) return false;
|
||
//step #5 如果城市满员
|
||
if (TrainUnitActionCheckCityFullPop(actionParam)) showType = ShowType.Locked;
|
||
//step #6如果格子上面有单位,不能生产,不显示
|
||
if (TrainUnitActionCheckUnitOnGrid(actionParam)) return false;
|
||
//step #7 如果英雄在冷却cd
|
||
if (CheckGiantHasColdTime(actionParam)) showType = ShowType.Cold;
|
||
//step #8 如果英雄违反了UNIQUE或类似的技能如QUARTET
|
||
if (CheckHeroHasOne(actionParam)) return false;
|
||
|
||
if (_actionId.UnitType == UnitType.Giant
|
||
&& (gridData.Resource is ResourceType.Military or ResourceType.RemiliaMilitary or ResourceType.MoriyaMilitary))
|
||
return true;
|
||
}
|
||
return false;
|
||
|
||
|
||
}
|
||
|
||
public bool ExecuteViewAfter(CommonActionParams actionParams)
|
||
{
|
||
//step #0 如果不是真map 不做动画
|
||
if (Main.MapData != actionParams.MapData) return false;
|
||
|
||
//step #1 更新产兵的格子的renderMark
|
||
_finalCity.SetCityRenderer(actionParams.MapData);
|
||
|
||
//step #2 增加得分,然后处理得分动画
|
||
var startPos = Table.Instance.GridToWorld(_finalGrid);
|
||
int score = GetCost() * 5;
|
||
actionParams.PlayerData.AddFaith(score,startPos);
|
||
|
||
AchievementDataManager.Instance.OnTrainUnit(actionParams.MapData, actionParams.PlayerData, actionParams.CityData, _newUnit);
|
||
|
||
return false;
|
||
}
|
||
|
||
}
|
||
|
||
//训练kaguya_french特殊兵种 animalWarrior
|
||
public class TrainUnitActionTrainKaguyaFrenchAnimalWarrior : TrainUnitAction
|
||
{
|
||
public TrainUnitActionTrainKaguyaFrenchAnimalWarrior(CommonActionId id) : base(id){}
|
||
|
||
protected override bool Execute(CommonActionParams actionParams)
|
||
{
|
||
//if (!CheckCan(actionParams)) return false;
|
||
|
||
//step #1 获取grid所在的city,设置基本数据
|
||
actionParams.MapData.GetCityDataByTerritoryGid(actionParams.GridData.Id, out var cityData);
|
||
//step #2 如果生产格子上有单位,先把他移开
|
||
if(actionParams.MapData.GetUnitDataByGid(actionParams.GridData.Id,out var unit)) Main.UnitLogic.PassiveMoveAway(actionParams.MapData,unit);
|
||
//step #3 生产单位
|
||
if(!actionParams.MapData.AddUnitData(actionParams.GridData.Id,cityData.Id,new UnitFullType(_actionId.UnitType,_actionId.GiantType,0),out var newUnit))
|
||
return false;
|
||
//step #4 扣钱
|
||
actionParams.PlayerData.SpendCoin( GetCost());
|
||
|
||
//step #5 消除动物
|
||
actionParams.GridData.Resource = ResourceType.None;
|
||
|
||
|
||
//Step #6 更新视野
|
||
var count = Main.PlayerLogic.UpdateSight_LogicView(actionParams.MapData,actionParams.PlayerData,actionParams.MapData.GridMap.GetAroundGridIdList(newUnit.GetSightRange(actionParams.MapData),actionParams.GridData));
|
||
newUnit.HeroTask(actionParams.MapData)?.OnExploredGrids(actionParams.MapData, newUnit, count);
|
||
foreach (var kv in actionParams.PlayerData.PlayerHeroData.HeroTaskDict) kv.Value.OnAnyExploredGrids(actionParams.MapData, newUnit, count);
|
||
|
||
//Step #7 更新所有建筑的buildingLevel(目前主要是影响kaguyaFrenchYard
|
||
Main.PlayerLogic.UpdateTerritoryAllBuildingLevel(actionParams.MapData,actionParams.PlayerData.Id);
|
||
|
||
//step #7 如果是真mapdata,处理视觉
|
||
if (Main.MapData == actionParams.MapData)// && actionParams.PlayerData.Id == actionParams.MapData.PlayerMap.SelfPlayerData.Id)
|
||
{
|
||
actionParams.GridData.Renderer(actionParams.MapData)?.InstantUpdateGrid(true);
|
||
var startPos = Table.Instance.GridToWorld(actionParams.GridData);
|
||
int score = GetCost() * 5;
|
||
actionParams.PlayerData.AddFaith(score,startPos);
|
||
AchievementDataManager.Instance.OnTrainUnit(actionParams.MapData, actionParams.PlayerData, actionParams.CityData, newUnit);
|
||
}
|
||
return true;
|
||
}
|
||
|
||
public override bool CheckCan(CommonActionParams actionParam)
|
||
{
|
||
//step #0 基础鲁棒性
|
||
if(_actionId.UnitType != UnitType.KaguyaFrenchAnimalWarrior) return false;
|
||
if (!TrainUnitActionCheckBaseData(actionParam)) return false;
|
||
//Step #1 如果不是grid产兵,直接return ,该兵种只能在grid产
|
||
if (actionParam.MainObjectType != MainObjectType.Grid) return false;
|
||
//Step #2 如果不再自家领地上操作 也不行
|
||
if (!TrainUnitActionCheckGridBelongPlayer(actionParam)) return false;
|
||
//step #3如果没科技 不行
|
||
if(!TrainUnitActionCheckHasTech(actionParam)) return false;
|
||
//step #4 如果城市上面有敌人单位,不行(自己人是可以顶的,盟友也不行)
|
||
if (TrainUnitActionCheckEnemyUnitOnGrid(actionParam)) return false;
|
||
//step #5 如果不是在animal上面,不行
|
||
if (actionParam.GridData.Resource != ResourceType.Animal) return false;
|
||
//step #6 如果没钱,不行
|
||
if (!TrainUnitActionCheckMoneyEnough(actionParam)) return false;
|
||
return true;
|
||
|
||
}
|
||
public override bool CheckShow(CommonActionParams actionParam,out ShowType showType)
|
||
{
|
||
showType = ShowType.None;
|
||
//step #0 基础鲁棒性
|
||
if(_actionId.UnitType != UnitType.KaguyaFrenchAnimalWarrior) return false;
|
||
if (!TrainUnitActionCheckBaseData(actionParam)) return false;
|
||
//Step #1 如果不是grid产兵,直接return ,该兵种只能在grid产
|
||
if (actionParam.MainObjectType != MainObjectType.Grid) return false;
|
||
//Step #2 如果不再自家领地上操作 也不行
|
||
if (!TrainUnitActionCheckGridBelongPlayer(actionParam)) return false;
|
||
//step #3如果没科技 不行
|
||
if(!TrainUnitActionCheckHasTech(actionParam)) return false;
|
||
//step #4 如果城市上面有敌人单位,不行(自己人是可以顶的,盟友也不行)
|
||
if (TrainUnitActionCheckEnemyUnitOnGrid(actionParam)) return false;
|
||
//step #5 如果不是在animal上面,不行
|
||
if (actionParam.GridData.Resource != ResourceType.Animal) return false;
|
||
//step #6 如果没钱,也可以显示
|
||
//if (!TrainUnitActionCheckMoneyEnough(actionParam)) return false;
|
||
return true;
|
||
}
|
||
|
||
}
|
||
} |