You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

349 lines
16 KiB

using System;
using System.Collections.Generic;
using AOT;
using GAS.Runtime;
using NavMeshPlus.Components;
using Sog;
using UnityEngine;
namespace CoreGame.Render
{
/// <summary>
/// 创建实体的服务,虽然没有英雄,怪物等概念,但实际是需要有,
/// TODO: 逻辑表现的实体ID要一直
/// </summary>
public static class EntityCreateSrv
{
public static void CreateBattleTeam()
{
// 创建英雄
var heroEntity = CreateHeroEntity(Contexts.Combat, CoreUIBridge.BattleInfoParams.heroSkinId);
heroEntity.transformProxy.SetPosition(CoreUIBridge.BattleInfoParams.playerBronPosition);
heroEntity.transformProxy.SetDirection(Vector3.right);
// heroEntity.TagAggregator.AddFixedTag(GTagLib.State_CannotBeOppoCatch);
BattleModule.s_LocalPlayerEid = heroEntity.creationIndex;
#if UNITY_EDITOR
BattleSimulateData.AttachTest(heroEntity);
#endif
}
public static CombatEntity CreateHeroEntity(CombatContext context, int heroSkinId)
{
var showCfg = RoleModelDescMgr.Instance.GetConfig(heroSkinId);
var ce = context.CreateEntity("Hero" + heroSkinId);
PropertySrv.GetHeroBasePropValue(ce);
ce.AddCommandReceiver(ce);
ce.isHero = true;
ce.AddBlackboard(CfgType.HeroCfg, heroSkinId, new[] { heroSkinId }, Array.Empty<int>(), ce.creationIndex,
false);
ce.AddFaction(Faction.Player, SelectUseType.Actor);
ce.AddTransformProxy(Vector2.zero, Vector2.right, ce);
ce.AddAudio(ce.creationIndex);
AbilitySrv.AttachActiveAbilityGroup(CommParamDescMgr.Instance.RoleDefaultSki.int_val, ce);
ce.AddAsset(new MainAssetParam()
{
path = $"{showCfg.folderPath}/{showCfg.prefabAnim}.prefab",
parentNodeName = "RenderWorld",
scaleParam = 1,
}, null);
var subAssetData = SptPool<SubAssetData>.Malloc();
subAssetData.Awake(ce.creationIndex, CoreUIBridge.BattleInfoParams.wingPath, BindPointType.Wing, null);
ce.asset.PushMainPartAsset(ref subAssetData);
// ce.blackboard.SetBornPos(ce.logicTransform.position);
Contexts.Combat.localPlayerEid = ce.creationIndex;
ce.isLocalPlayer = true;
ce.isAttractor = true;
ce.AddEquips(ce);
ce.equips.SwitchSlotNoCheck(CoreUIBridge.BattleInfoParams.equipInfo.currentGunSlot);
GunSrv.DynamicEquipGun(ce, CoreUIBridge.BattleInfoParams.equipInfo);
return ce;
}
public static CombatEntity CreateCameraEntity(CombatContext context, string prefabPath)
{
var combatEntity = context.CreateEntity("VirtualCamera");
combatEntity.AddAsset(
new MainAssetParam()
{
path = prefabPath,
parentNodeName = "RenderWorld",
scaleParam = 1,
}, null);
// combatEntity.LoadAsset();
return combatEntity;
}
public static CombatEntity CreateJumpTextEntity(CombatContext context, object initData = null)
{
var combatEntity = context.SetJumpText(new Queue<HurtData>());
combatEntity.Name = "JumpText";
return combatEntity;
}
public static CombatEntity CreateJoystickEntity(CombatContext context, object initData = null)
{
var combatEntity = context.CreateEntity("JoystickEntity");
combatEntity.AddAsset(
new MainAssetParam()
{
path = "Model/Joystick",
parentNodeName = "UICanvas/GlobalWindowManager/JoyStick",
scaleParam = 1,
}, null);
// combatEntity.LoadAsset();
return combatEntity;
}
public static CombatEntity[] CreateObstacleEntities(CombatContext context, object initData = null)
{
const int componentIndex = CombatComponentsLookup.Collider2DProxy;
var modifiers = NavMeshModifier.activeModifiers;
var gameObject = new GameObject("ObstacleEntities_Logic");
var allObstacle = context.CreateEntity("ObstacleEntities_Logic");
allObstacle.isObstacle = true;
allObstacle.AddFaction(Faction.None, SelectUseType.Obstacle, Faction.None);
var proxy = (Collider2DProxy)allObstacle.CreateComponent(componentIndex,
CombatComponentsLookup.componentTypes[componentIndex]);
allObstacle.AddComponent(componentIndex, proxy);
allObstacle.AddTransformProxy(Vector2.zero, Vector2.right, allObstacle);
(proxy).Init(gameObject, allObstacle);
AbilitySrv.GrantBaseAbility(allObstacle);
allObstacle.TagCountContainer.UpdateTagCount(GTagLib.Entity_Obstacle, 1);
var fac = allObstacle.faction;
for (var i = 0; i < modifiers.Count; i++)
{
var modifier = modifiers[i];
if (modifier.TryGetComponent<Collider2D>(out var collider2D))
{
proxy.FillColliderByInit(collider2D, fac, true);
}
}
return null;
}
public static void CreateSummonEntities(GameAbilityContext ctx, int summonId)
{
var tbSummon = SummonDescMgr.Instance.GetConfig(summonId);
var summoner = ctx.ownerEnt;
var summonerFaction = summoner.faction;
var queryParam = new QueryParam
{
faction = summonerFaction.faction,
selectUseType = SelectUseType.Summon
};
var friendSummon = Contexts.Combat.GetEntitiesWithFactionCommonBeQueryParam(queryParam);
int existAmount = 0;
foreach (var ent in friendSummon)
{
if (ent.summon.summonId == summonId)
existAmount++;
}
var summonAmount = (float)ExpressionEvaluator.CalcVal_WithCtx(tbSummon.summonAmount, ctx, 2f);
var summonAmountMax = (float)ExpressionEvaluator.CalcVal_WithCtx(tbSummon.maxAmount, ctx, 3f);
var summonCount = summonAmount + existAmount < summonAmountMax
? (int)summonAmount
: (int)summonAmountMax - existAmount;
if (summonCount == 0)
{
return;
}
var summonerPos = Vector2.zero ;//summoner.logicTransform.position;
var summonDistance = (float)ExpressionEvaluator.CalcVal_WithCtx(tbSummon.summonDistance, ctx, 5f);
var maxSurvivalTime = (float)ExpressionEvaluator.CalcVal_WithCtx(tbSummon.maxTime, ctx, 5f);
var survivalParam1 = (float)ExpressionEvaluator.CalcVal_WithCtx(tbSummon.survivalParam1, ctx, 10f);
var survivalType = tbSummon.survivalType;
var tbMonster = MonsterPropDescMgr.Instance.GetConfig(tbSummon.monsterID);
// var res = new CombatEntity[summonCount];
for (var i = 0; i < summonCount; i++)
{
var ce = Contexts.Combat.CreateEntity("Summon" + tbMonster.name);
ce.AddFaction(summonerFaction.faction, SelectUseType.Summon);
PropertySrv.GetMonsterPropValue(ce, tbMonster.id);
var propertyComponent = ce.property;
propertyComponent.SetLinkEid(summoner.creationIndex);
propertyComponent.SetLinkProperty(PropertyDef.Level);
if (string.IsNullOrEmpty(tbSummon.hpFixedInc) == false)
{
var totalHp = ExpressionEvaluator.CalcVal_WithCtx(tbSummon.hpFixedInc, ctx, 0);
propertyComponent.SetProperty(PropertyDef.HpFixedIncrease, totalHp, true);
propertyComponent.SetProperty(PropertyDef.CurHp, totalHp, true);
}
if (string.IsNullOrEmpty(tbSummon.atkFixedInc) == false)
{
var atk = ExpressionEvaluator.CalcVal_WithCtx(tbSummon.atkFixedInc, ctx, 0);
propertyComponent.SetProperty(PropertyDef.AtkFixedIncrease, atk, true);
}
if (string.IsNullOrEmpty(tbSummon.defFixedInc) == false)
{
var def = ExpressionEvaluator.CalcVal_WithCtx(tbSummon.defFixedInc, ctx, 0);
propertyComponent.SetProperty(PropertyDef.DefFixedIncrease, def, true);
}
var affixIds = GetMonsterRandomAffixIds(tbMonster);
ce.AddBlackboard(CfgType.MonsterCfg, tbMonster.id, Array.Empty<int>(), affixIds,
ce.creationIndex, tbMonster.NoChangeDir == 0);
ce.AddSummon(summonId, maxSurvivalTime, survivalType, survivalParam1);
if (tbSummon.dieWithSummoner != 0)
{
var lifeBindMeComponent = summoner.lifeBindMe;
if (lifeBindMeComponent == null)
{
summoner.AddLifeBindMe(summoner);
lifeBindMeComponent = summoner.lifeBindMe;
}
lifeBindMeComponent.AddChild(ce.creationIndex, i == 0);
}
ce.AddParentRecorder(CompLinkerType.Summon2C, summoner.creationIndex);
if (summonerFaction.faction == Faction.Player)
ce.isPartner = true;
else
ce.AddMonster(tbMonster.type);
AbilitySrv.AttachActiveAbilityGroup(tbMonster.skillGroup, ce);
AttachAffixTalentToEntity(ce);
for (int j = 0; j < tbMonster.AssetTags.Length; j++)
{
var gameplayTag = AbilitySrv.GetGameplayTag(tbMonster.AssetTags[j]);
ce.TagCountContainer.AddFixedTag(gameplayTag);
}
ce.AddAsset(
new MainAssetParam
{
path = tbMonster.prefab,
parentNodeName = "RenderWorld",
scaleParam = 1,
}, null);
// ce.LoadAsset();
var randomPos2D = MathHelper.OnsideUnitCircleRandom(summonDistance);
// summonerPos = summonerPos + randomPos2D;
// var vector2 = MathViewUtils.ToVector2(summonerPos);
// NavMesh.SamplePosition(fixed64Vector2, out var closestHit, 10f, NavMesh.AllAreas);
// var pos = new Vector2(closestHit.position.x, closestHit.position.y);
// ce.AddLogicTransform(summonerPos, Fixed64Vector2.one, Fixed64Vector2.right);
// ce.AddTransformProxy(summonerPos.ToVector2(), Vector2.right, ce);
ce.AddAudio(ce.creationIndex);
ce.blackboard.SetBornPos(ce.logicTransform.position, randomPos2D);
}
}
public static CombatEntity BronMonsterEntity(CombatContext context, CombatEntity parentEnt,
ref MonsterData monsterData)
{
var tbMonster = MonsterPropDescMgr.Instance.GetConfig(monsterData.unitId);
if (tbMonster == null)
return null;
var ce = context.CreateEntity("Monster" + tbMonster.name);
var affixIds = GetMonsterRandomAffixIds(tbMonster);
ce.AddBlackboard(CfgType.MonsterCfg, monsterData.unitId, Array.Empty<int>(), affixIds,
ce.creationIndex, tbMonster.NoChangeDir == 0);
// var hasHit = NavMesh.Raycast(monsterData.srcPos, monsterData.position, out var closestHit, NavMesh.AllAreas);
// // var isSucc = NavMesh.SamplePosition(monsterData.position, out var closestHit, 10f, NavMesh.AllAreas);
// if (hasHit)
// {
// var normalDir = new Vector2(closestHit.normal.x, closestHit.normal.y);
// Vector2 newPos = closestHit.position;
// monsterData.position = newPos + normalDir * monsterData.pushRadius;
// NavMesh.SamplePosition(monsterData.position, out var closestHit2, 10f, NavMesh.AllAreas);
// monsterData.position = new Vector2(closestHit2.position.x, closestHit2.position.y);
// }
ce.AddLogicTransform(monsterData.position, Fixed64Vector2.one, Fixed64Vector2.right);
ce.blackboard.SetBornPos(ce.logicTransform.position);
// if (parentEnt != null)
// ce.AddParentRecorder(CompLinkerType.Summon2C, parentEnt.creationIndex);
ce.AddEffectShowProxy(tbMonster.VFXsize * BattleConst.TenThousandReverse.AsFloat, ce);
ce.AddBorn(tbMonster.bornTime * BattleConst.TenThousandReverse.AsFloat, tbMonster.bornVFX);
return ce;
}
public static CombatEntity CreateMonsterByBorn(CombatEntity ce)
{
var blackboard = ce.blackboard;
var tbMonster = MonsterPropDescMgr.Instance.GetConfig(blackboard.unitCfgId);
ce.AddMonster(tbMonster.type);
PropertySrv.GetMonsterPropValue(ce, tbMonster.id);
// 阵营要先设置,碰撞有依赖
ce.AddFaction(Faction.Enemy, SelectUseType.Actor);
ce.AddAudio(ce.creationIndex);
AbilitySrv.AttachActiveAbilityGroup(tbMonster.skillGroup, ce);
AttachAffixTalentToEntity(ce);
if (tbMonster.type == MonsterType.Boss)
{
ce.TagCountContainer.AddFixedTag("Entity.Monster.Boss");
// 添加可再生护盾
if (tbMonster.ShieldValue > 0)
{
ce.AddRefreshableHpShield(tbMonster.ShieldType, tbMonster.ShieldValue,
tbMonster.ShieldRestore * 0.001f);
ce.AddReload(0);
}
}
ce.AddAsset(
new MainAssetParam()
{
path = tbMonster.prefab,
parentNodeName = "RenderWorld",
scaleParam = 1,
}, null);
// ce.LoadAsset();
var levelWaveEntity = Contexts.Combat.LevelWave;
levelWaveEntity.DispatchEvent(ClientEvent.LevelMonsterRage, null);
return ce;
}
public static int[] GetMonsterRandomAffixIds(MonsterPropDesc tbMonster)
{
var randomAffixes = tbMonster.randomAffixes;
if (randomAffixes == 0)
{
return Array.Empty<int>();
}
var affixesRandomGroupDesc = AffixesRandomGroupDescMgr.Instance.GetConfig(randomAffixes);
if (affixesRandomGroupDesc == null || affixesRandomGroupDesc.affixesGroup.Length == 0)
{
return Array.Empty<int>();
}
var affixesRandomGroup = affixesRandomGroupDesc.affixesGroup;
var randomIndex = RandomSrv.Range(0, affixesRandomGroup.Length);
var affixesId = affixesRandomGroup[randomIndex];
var affixes = AffixesDescMgr.Instance.GetConfig(affixesId);
var affixIds = new int[affixes.affixes.Length];
for (var i = 0; i < affixes.affixes.Length; i++)
{
var affixId = affixes.affixes[i];
affixIds[i] = affixId;
}
return affixIds;
}
public static void AttachAffixTalentToEntity(CombatEntity ce)
{
var blackboard = ce.blackboard;
if (ce.blackboard == null)
return;
for (int i = 0; i < blackboard.affixIds.Length; i++)
{
var affixId = blackboard.affixIds[i];
var affix = AffixDescMgr.Instance.GetConfig(affixId);
AbilitySrv.AttachTalent_WithGaParam(ce, affix.talentID, null, 1);
}
}
}
}