---@class UGCPlayerPawn_C:BP_UGCPlayerPawn_C --Edit Below-- ---@type UGCPlayerPawn_C local UGCPlayerPawn = { ---@field ModifyDamageDelegation fun(DamageAmount:float,DamageEvent:FDamageEvent,EventInstigator:AController,DamageCauser:AActor):float ModifyDamageDelegation = {}; MechanismEnergy = 0; -- 玩家拥有的能量 CachedSTCharacterMovementGravityScale = 1.0; BaseCapsuleHalfHeight = 88.0; BaseCapsuleRadius = 40; }; function UGCPlayerPawn:GetReplicatedProperties() return "MechanismEnergy" end -- 关闭盒子掉落 function UGCPlayerPawn:IsSkipSpawnDeadTombBox(EventInstigater) return true end function UGCPlayerPawn:ReceiveBeginPlay() self.SuperClass.ReceiveBeginPlay(self); --- 设置翻墙功能 self.bVaultIsOpen = true --- 设置滑铲功能 self.IsOpenShovelAbility = true UGCEventSystem.SendEvent(EventEnum.PlayerBeginPlay, self) --- 获取初始胶囊体信息 self.BaseCapsuleHalfHeight = self.CapsuleComponent.CapsuleHalfHeight self.BaseCapsuleRadius = self.CapsuleComponent.CapsuleRadius if self:HasAuthority() then self:AddEvent() self:InitParam() --- 循环判断当前武器配置是否正确,多则删、少则补 self.LoopCheckGradientWeaponHandle = UGCEventSystem.SetTimerLoop(self, self.CheckGradientWeapon, 1.) --- 循环判断是否给予初始近战武器,有则移除Handle,没有则进行循环 self.AddDefaultMeleeWeaponHandle = UGCEventSystem.SetTimerLoop(self, self.AddDefaultMeleeWeapon, 1.) --- 循环判断默认装备是否有给予 self.DefaultBackPack = TableHelper.DeepCopy(GlobalConfigs.GameSetting.BeBornItems) self.CheckBornItemsHandle = UGCEventSystem.SetTimerLoop(self, self.CheckBornItems, 1.) --end if UE.IsValid(self:GetController()) then self:ReceivePossessed(self:GetController()) UGCLogSystem.Log("[UGCPlayerPawn_ReceiveBeginPlay] Controller Is Valid") end -- Test --UGCEventSystem.SetTimer(self, function() -- local SelfPos = self:K2_GetActorLocation() -- SelfPos.Z = -700 -- self:SetPawnTF(SelfPos, self:K2_GetActorRotation()) --end --,10) -- Test End else end end --- 客户端必定执行的BeginPlay function UGCPlayerPawn:ClientMustBeExeBeginPlay() if self.DoOnceMustBeExeBeginPlay then return end self.DoOnceMustBeExeBeginPlay = true end function UGCPlayerPawn:CheckGradientWeapon() WeaponGradientManager.UpdatePlayerGradientWeaponMatching( self.PlayerKey, UGCGameSystem.GameState:GetPlayerWeaponGrade(self.PlayerKey), UGCGameSystem.GameState:GetPlayerDefaultMeleeWeaponByPlayerKey(self.PlayerKey) ) local MainShootWeapon2 = UGCWeaponManagerSystem.GetWeaponBySlot(self, ESurviveWeaponPropSlot.SWPS_MainShootWeapon2) if MainShootWeapon2 then local ItemID = UGCWeaponManagerSystem.GetWeaponItemID(MainShootWeapon2) UGCBackPackSystem.DropItem(self, ItemID, UGCBackPackSystem.GetItemCount(self, ItemID), true) UGCLogSystem.Log("[UGCPlayerPawn_CheckGradientWeapon] ItemID:%s", tostring(ItemID)) end end function UGCPlayerPawn:AddDefaultMeleeWeapon() local MeleeWeaponID = UGCGameSystem.GameState:GetPlayerDefaultMeleeWeaponByPlayerKey(self.PlayerKey) if UGCBackPackSystem.GetItemCount(self, MeleeWeaponID) > 0 then UGCEventSystem.StopTimer(self.AddDefaultMeleeWeaponHandle) self.AddDefaultMeleeWeaponHandle = nil else UGCBackPackSystem.AddItem(self, MeleeWeaponID, 1) end end function UGCPlayerPawn:CheckBornItems() UGCLogSystem.Log("[UGCPlayerPawn_CheckBornItems] PlayerKey:%s", tostring(self.PlayerKey)) for i = #self.DefaultBackPack, 1, -1 do local ItemID = self.DefaultBackPack[i].ItemID local Count = self.DefaultBackPack[i].Count local InstCount = UGCBackPackSystem.GetItemCount(self, ItemID) if InstCount >= Count then self.DefaultBackPack[i] = nil else UGCBackPackSystem.AddItem(self, ItemID, Count - InstCount) end end if #self.DefaultBackPack == 0 then UGCEventSystem.StopTimer(self.CheckBornItemsHandle) self.CheckBornItemsHandle = nil UGCLogSystem.Log("[UGCPlayerPawn_CheckBornItems] Succeed PlayerKey:%s", tostring(self.PlayerKey)); end end function UGCPlayerPawn:InitParam() if UGCGameSystem.GameState:GetGameStateType() == CustomEnum.EGameState.Waiting then self:SetMechanismEnergy(GlobalConfigs.GameSetting.WaitingInitEnergy) else self:SetMechanismEnergy(GlobalConfigs.GameSetting.InitEnergy) end end function UGCPlayerPawn:ReceiveTick(DeltaTime) self.SuperClass.ReceiveTick(self, DeltaTime); if not UGCGameSystem.IsServer() then self:ClientMustBeExeBeginPlay() end end function UGCPlayerPawn:ReceiveEndPlay() self.SuperClass.ReceiveEndPlay(self); self:RemoveEvent() end function UGCPlayerPawn:AddEvent() if self:HasAuthority() then self.DeadNotifyDelegate:Add(self.PlayerDead, self) self.DamageNotifyDelegate:Add(self.PlayerInjury, self) else end end function UGCPlayerPawn:RemoveEvent() if self:HasAuthority() then self.DeadNotifyDelegate:Remove(self.PlayerDead, self) self.DamageNotifyDelegate:Remove(self.PlayerInjury, self) if self.LoopCheckGradientWeaponHandle then UGCEventSystem.StopTimer(self.LoopCheckGradientWeaponHandle) self.LoopCheckGradientWeaponHandle = nil end if self.AddDefaultMeleeWeaponHandle then UGCEventSystem.StopTimer(self.AddDefaultMeleeWeaponHandle) self.AddDefaultMeleeWeaponHandle = nil end if self.CheckBornItemsHandle then UGCEventSystem.StopTimer(self.CheckBornItemsHandle) self.CheckBornItemsHandle = nil end else end end function UGCPlayerPawn:ReceivePossessed(NewController) self.SuperClass.ReceivePossessed(self, NewController); UGCLogSystem.Log("[UGCPlayerPawn_ReceivePossessed] PlayerKey:%s", tostring(NewController.PlayerKey)) UGCEventSystem.SendEvent(EventEnum.PlayerPossessed, NewController.PlayerKey) UGCGameSystem.GameState:SetPlayerIsAlive(NewController.PlayerKey, self) end -------------------------------------------------- Delegate -------------------------------------------------- ---@param DamageInfo FDamageInfoCollection ---@return VictimKey, CauserKey, WeaponID, DamageType, IsHeadShotDamage, Distance, DamageValue uint, uint, int, EDamageType, bool, float, float function UGCPlayerPawn:GetDamageInfoCollectionInfo(DamageInfo) local CauserController = DamageInfo.Instigator local WeaponID = -1 local CauserKey = CauserController and CauserController.PlayerKey or -1 local VictimKey = self.PlayerKey local CauserItemID = DamageInfo.CauserItemID --- 近战投掷、投掷手雷 if CauserItemID then WeaponID = CauserItemID end UGCLogSystem.Log("[UGCPlayerPawn_GetDamageInfoCollectionInfo] WeaponID:%d", WeaponID) local Distance = 0. if CauserController and CauserController.Pawn then Distance = VectorHelper.GetDistance(self:K2_GetActorLocation(), CauserController.Pawn:K2_GetActorLocation()) end local IsHeadShotDamage = (DamageInfo.Hit.BoneName == "head") return VictimKey, CauserKey, WeaponID, DamageInfo.DamageType, IsHeadShotDamage, Distance, DamageInfo.Damage end ---@param DamageInfo FDamageInfoCollection function UGCPlayerPawn:PlayerDead(DamageInfo) local VictimKey, CauserKey, WeaponID, DamageType, IsHeadShotDamage, Distance, DamageValue = self:GetDamageInfoCollectionInfo(DamageInfo) UGCSendRPCSystem.RPCEvent(nil, EventEnum.PlayerDeathInfo, VictimKey, CauserKey, WeaponID, DamageType, IsHeadShotDamage, Distance, DamageValue) UGCEventSystem.SendEvent(EventEnum.PlayerDeathInfo, VictimKey, CauserKey, WeaponID, DamageType, IsHeadShotDamage, Distance, DamageValue) UGCGameSystem.GameState:SetPlayerIsAlive(VictimKey, nil) end ---@param DamageInfo FDamageInfoCollection ---@param ReturnValue float function UGCPlayerPawn:PlayerInjury(DamageInfo) local VictimKey, CauserKey, WeaponID, DamageType, IsHeadShotDamage, Distance, DamageValue = self:GetDamageInfoCollectionInfo(DamageInfo) UGCSendRPCSystem.RPCEvent(CauserKey, EventEnum.PlayerInjuryInfo, VictimKey, CauserKey, WeaponID, DamageType, IsHeadShotDamage, Distance, DamageValue) end ------------------------------------------------ Delegate End ------------------------------------------------ function UGCPlayerPawn:AddMechanismEnergy(InEnergy) self:SetMechanismEnergy(self:GetMechanismEnergy() + InEnergy) end function UGCPlayerPawn:GetMechanismEnergy() return self.MechanismEnergy end function UGCPlayerPawn:SetMechanismEnergy(NewEnergy) self.MechanismEnergy = (NewEnergy > 0 and NewEnergy or 0) end ------------------------------------------------ ModifyDamage ------------------------------------------------ function UGCPlayerPawn:UGC_TakeDamageOverrideEvent(Damage, DamageType, EventInstigator, DamageCauser, Hit) local DamageAmount = Damage UGCLogSystem.Log("[UGCPlayerPawn_UGC_TakeDamageOverrideEvent] InDamageAmount:%s", tostring(DamageAmount)) if EventInstigator and EventInstigator.PlayerKey then local CauserTeamID = UGCPlayerStateSystem.GetTeamID(EventInstigator.PlayerKey) local SelfTeamID = UGCPlayerStateSystem.GetTeamID(self.PlayerKey) if DamageType == EDamageType.UGCPointDamage then DamageAmount = (CauserTeamID == SelfTeamID and MechanismConfig.MechanismFriendlyInjuryRatio * DamageAmount or DamageAmount) else if EventInstigator.PlayerKey == self.PlayerKey and GlobalConfigs.GameSetting.bEnableSelfHarm then --- 对自己的伤害 DamageAmount = GlobalConfigs.GameSetting.SelfHarmInjuryRatio * DamageAmount else --- 伤害设置(友方、敌方) DamageAmount = (CauserTeamID == SelfTeamID and GlobalConfigs.GameSetting.FriendlyInjuryRatio * DamageAmount or DamageAmount) end end elseif DamageCauser and DamageCauser:GetOwner() then UGCLogSystem.Log("[UGCPlayerPawn_UGC_TakeDamageOverrideEvent] DamageCauser:GetOwner():%s", KismetSystemLibrary.GetObjectName(DamageCauser:GetOwner())) local TargetPlayerKey = DamageCauser:GetOwner().PlayerKey if TargetPlayerKey then local CauserTeamID = UGCPlayerStateSystem.GetTeamID(TargetPlayerKey) local SelfTeamID = UGCPlayerStateSystem.GetTeamID(self.PlayerKey) DamageAmount = (CauserTeamID == SelfTeamID and GlobalConfigs.GameSetting.FriendlyInjuryRatio * DamageAmount or DamageAmount) end else --- 掉落伤害 DamageAmount = GlobalConfigs.GameSetting.bEnableDropDamage and DamageAmount or 0. end if DamageType == EDamageType.MeleeDamage then DamageAmount = DamageAmount * GlobalConfigs.GameSetting.MeleeDamageScale end UGCLogSystem.Log("[UGCPlayerPawn_UGC_TakeDamageOverrideEvent] ModifyDamageAmount:%s", tostring(DamageAmount)) return DamageAmount end ---------------------------------------------- ModifyDamage End ---------------------------------------------- function UGCPlayerPawn:SetPawnTF(Pos, Rot) self:K2_SetActorLocation(Pos) self:K2_SetActorRotation(Rot) self.CharacterMovement.Velocity = VectorHelper.VectorZero() if UGCGameSystem.IsServer() then self.bShouldDumpCallstackWhenMovingfast = false self:SetClientLocationOrRotation(Pos, Rot, true, false) self.bShouldDumpCallstackWhenMovingfast = true UGCSendRPCSystem.ActorRPCNotify(nil, self, "SetPawnTF", VectorHelper.ToLuaTable(Pos), VectorHelper.RotToLuaTable(Rot)) UGCLogSystem.Log("[UGCPlayerPawn_SetPawnTF] Succeed") end end function UGCPlayerPawn:ScalePlayer(NewScale) if UGCGameSystem.IsServer() then self:SetPlayerScale_N(NewScale) UGCLogSystem.Log("[UGCPlayerPawn_ScalePlayer]") UGCSendRPCSystem.ActorRPCNotify(nil, self, "SetPlayerScale_N", NewScale) UGCLogSystem.Log("[UGCPlayerPawn_ScalePlayer] Finish") end end function UGCPlayerPawn:SetPlayerScale_N(NewScale) UGCLogSystem.Log("[UGCPlayerPawn_SetPlayerScale_N]") local HalfHeight = self.BaseCapsuleHalfHeight * NewScale self.Mesh:SetWorldScale3D({X = NewScale, Y = NewScale, Z = NewScale}) self.CapsuleComponent:SetCapsuleHalfHeight(HalfHeight, true) self.CapsuleComponent:SetCapsuleRadius(self.BaseCapsuleRadius * NewScale, true) self.Mesh:K2_SetRelativeLocation({X = 0, Y = 0, Z = HalfHeight}) UGCLogSystem.Log("[UGCPlayerPawn_SetPlayerScale_N] Finish") end function UGCPlayerPawn:GetAvailableServerRPCs() return end return UGCPlayerPawn;